在Perl的数值lt(<;)第25行中使用未初始化值$guess
我对Perl非常陌生,并被分配了一个简单的猜测游戏,在这个游戏中,用户有8次机会猜测1到100之间的数字。我不断地得到上面提到的错误,无法找出它 这是我的密码:在Perl的数值lt(<;)第25行中使用未初始化值$guess,perl,random,Perl,Random,我对Perl非常陌生,并被分配了一个简单的猜测游戏,在这个游戏中,用户有8次机会猜测1到100之间的数字。我不断地得到上面提到的错误,无法找出它 这是我的密码: use Modern::Perl; my ($guess,$target,$counter); $target = (int rand 100) + 1; while ($guess < $target) { chomp ($guess=<>);
use Modern::Perl;
my ($guess,$target,$counter);
$target = (int rand 100) + 1;
while ($guess < $target)
{
chomp ($guess=<>);
print "Enter guess $counter: ";
$counter++;
if ($guess eq $target) {
print "\nCongratulations! You guessed the secret number $target in $counter";
}
elsif ($guess > $target) {
print "\nYour guess, $guess, is too high.";
}
elsif ($guess < $target) {
print "\nYour guess, $guess, is too low.";
}
else {
print "You lose. The number was $target.";
}
}
使用Modern::Perl;
我的($guess,$target,$counter);
$target=(国际兰特100)+1;
而($guess<$target)
{
chomp($guess=);
打印“输入猜测$counter:”;
$counter++;
if($GUSE eq$目标){
打印“\n密码!您在$counter中猜到了密码$target”;
}
elsif($guess>$target){
打印“\n您的猜测,$guess太高。”;
}
elsif($guess<$target){
打印“\n您的猜测,$guess太低。”;
}
否则{
打印“你输了,号码是$target。”;
}
}
这里的问题是没有显式初始化变量。默认情况下,Perl将使用my()
创建的变量初始化为unde
值。请看一下脚本中的以下行:
my ($guess,$target,$counter);
此行创建三个变量,所有变量都设置为undef
。有关my()
运算符的输入和输出的更多详细信息,请查看。以下是该文档页面的相关引用:
如果需要,my()的参数列表可以指定给,这允许
您需要初始化变量。(如果没有为a提供初始值设定项
特定变量,它是使用未定义的值创建的。)
您的代码存在一些问题。以下是我的代码,使用不同的方法:
#!/usr/bin/perl
use 5.012; # use strict; use feature 'say';
use warnings;
my $number = (int rand 100) + 1;
my $max_guesses = 8;
GUESS: foreach my $guess_no (1..$max_guesses) {
say "($guess_no) Please enter a guess:";
my $guess = <>;
chomp $guess;
unless ($guess =~ /^\d+$/) {
say "Hey, that didn't look like a number!";
redo GUESS;
}
if ($guess == $number) {
say "Congrats, you were on target!";
last GUESS;
} elsif ($guess < $number) {
say "Nay, your guess was TOO SMALL.";
} elsif ($guess > $number) {
say "Nay, your guess was TOO BIG.";
} else {
die "Illegal state";
}
if ($guess_no == $max_guesses) {
say "However, you have wasted all your guesses. YOU LOOSE.";
last GUESS;
}
}
(所有其他极端情况(猜测太多,输入的不是数字)均按预期工作)
我做了什么不同的事
- 猜测太小时,我没有循环(← 臭虫。相反,我对每个猜测都进行了循环迭代。然而,
循环也可以工作while(1)
- 我使用一个简单的正则表达式对输入进行了健全性检查。它断言Perl将把输入视为数字。否则,你可以重新猜测
- 我一声明所有变量就初始化它们。这将消除错误消息中出现未初始化值的可能性
- 我使用适当的比较运算符。Perl标量有两种风格:stringy和numeric:
Stringy Numeric lt < le <= eq == ne != ge >= gt > cmp <=>
stringnumeric 中尉< 乐= gt> 化学机械抛光
函数像打印say
一样打印字符串,但附加一个换行符。这将删除字符串开头或结尾处的akwardprint
s。它使阅读代码更容易\n
- 你没有提到哪一行是第25行!这可能很重要
但是,请查看您的
while
语句。请注意,您正在将$guess
与$target
进行比较,但尚未设置$guess
。这是在内部设置的当循环时,您是。这就是为什么要得到未定义的变量
我也看不到$counter
设置在哪里。这也可能是一个问题
让我们看一下您的,而循环更近一点:
while ( $guess < $target ) {
blah, blah, blah
}
一种稍微好一点的方法是使用for循环:
for ( my $count = 1; $count <= 8; $count++ ) {
blah, blah, blah
}
(注意:有些人在做这种类型的循环时使用foreach
关键字,而不是for
关键字,以区别于C型for循环。然而,有些人(cough!Damian Conway,cough!)不赞成使用foreach
,因为它并没有真正增加清晰度。)
让我们看一下逻辑的另一个方面:
if ($guess eq $target) {
print "\nCongratulations! You guessed the secret number $target in $counter";
}
elsif ($guess > $target) {
print "\nYour guess, $guess, is too high.";
}
elsif ($guess < $target) {
print "\nYour guess, $guess, is too low.";
}
else { #Do this if the guess isn't equal to, greater than or less than the target
print "You lose. The number was $target.";
}
首先,
是null filehandle运算符,它与
非常非常不同:
null filehandle很特别:它可以用来模拟sed和awk的行为,以及任何其他接受文件名列表的Unix过滤程序,对所有文件名的每一行输入都执行相同的操作。来自的输入来自标准输入或命令行上列出的每个文件。它的工作原理如下:第一次求值时,将检查@ARGV数组,如果它为空,$ARGV[0]将设置为“-”,打开时将提供标准输入。然后将@ARGV数组作为文件名列表进行处理
您需要的是
还请注意,在打印提示之前,您将获得输入。您确实想这样做:
print "Enter guess $counter: ";
chomp ($guess = <STDIN>);
有几件事我没有涉及:
- 进行数值比较时,请使用
=
运算符,而不要使用eq
,这是用于字符串的
- 如果可以,我使用
说
而不是打印
。say
命令类似于print
,只是它会自动为我在末尾添加NL
- 注意
退出在我说你赢了之后。我想在那个时候结束我的计划
- 注意,在需要之前,我不会声明所有变量。在我的程序中,
$guess
和$counter
仅存在于for
循环中,而$target
同时存在于for
循环的内部和外部
- I
使用常量来帮助避免神秘数字。例如,1..MAX_guesss
帮助我理解循环将达到我的最大猜测,而1..8
无法解释为什么我要达到8。另外,我可以简单地改变我的常数,突然你猜一个1到1000之间的数字有10个变化
由于您向我们展示的脚本中只有25行代码,我们如何猜测您的$guess
未初始化在哪一行?请确保您的代码段和错误消息是自一致的。我猜这是while
行,它可能有错误的条件(如果你在做com,可能应该有!=
而不是)
for my $counter (1..8) {
blah, blah, blah
}
if ($guess eq $target) {
print "\nCongratulations! You guessed the secret number $target in $counter";
}
elsif ($guess > $target) {
print "\nYour guess, $guess, is too high.";
}
elsif ($guess < $target) {
print "\nYour guess, $guess, is too low.";
}
else { #Do this if the guess isn't equal to, greater than or less than the target
print "You lose. The number was $target.";
}
chomp ( $guess = <> );
print "Enter guess $counter: ";
print "Enter guess $counter: ";
chomp ($guess = <STDIN>);
#! /usr/bin/env perl
use strict;
use warnings;
use feature qw(say);
use constant {
UPPER_RANGE => 100,
MAX_GUESSES => 8,
};
$| = 1;
my $target = int ( ( rand UPPER_RANGE ) + 1 );
for my $counter (1..MAX_GUESSES) {
print "Enter guess #$counter: ";
chomp ( my $guess = <STDIN> );
if ($guess == $target) {
say "Congratulations! You guessed the secret number $target in $counter turns";
exit;
}
elsif ($guess > $target) {
say "Your guess, $guess, is too high.";
}
else {
say "Your guess, $guess, is too low.";
}
}
say "You lose. The number was $target.";