尝试使用foreach循环和推送perl程序,但代码无法运行

时间:2015-10-22 19:59:12

标签: perl

#!/usr/bin/perl
use strict;

my @primes =(2,3,5,7,11,13,17,19,23,29,31,37,41,43,47);

sub listprimes {
    my $n = shift;

    my @answer = ();

    foreach $a(@prime) {
        if($a<=$n){push @answer,$a;}

    return @answer;
}

sub random {
    my($a,$b) = @_;
    return int(rand($b-$a+1))+$a;
}

my $a = random(10,50);
my $f = listprimes($a);

print("f\n");

我使用foreach循环和push函数来编写它,但是我收到以下错误:

./listprime: line 3: use: command not found
./listprime: line 5: syntax error near unexpected token `('
./listprime: line 5: `my @primes =(2,3,5,7,11,13,17,19,23,29,31,37,41,43,47);'

请告诉我怎么纠正它。

3 个答案:

答案 0 :(得分:3)

您收到的这些错误不是由perl生成的;它们由bash生成。这意味着你以某种方式将脚本提供给shell。

也许您需要使文件可执行(例如chmod 700 listprime)。

还要确保#!是文件的前两个字符。 (od -c listprime | head -n 1应该0000000 # ! / u s r / b i n / p e r l \n。)

如果一切正常,您可以使用./listprime执行脚本。

解决该问题后,您需要在程序中修复许多问题。

#!/usr/bin/perl
use strict;                             +- Always use this as it finds many errors,
use warnings;                         <-+  although it woulnd't have helped you this time.

my @primes =(2,3,5,7,11,13,17,19,23,29,31,37,41,43,47);

sub listprimes {
    my $max = shift;                  <--- Try to use meaningful names.

    my @answer;                       <--- New arrays are already empty.

    foreach my $prime (@primes) {     <--- @primes was misspelled.
        if($prime<=$max){push @answer,$prime;}
    }                                 <--- This curly was missing. Proper indenting not 
                                           only makes code easier to read; it makes errors
    return @answer;                        like this obvious.
}

sub random {
    my($min,$max) = @_;               <--- Avoid using $a and $b as they are semi-special.
    return int(rand($max-$min+1))+$min;
}

my $max = random(10,50);
my @selected = listprimes($max);      <--- Use an array to store multiple values.

print("@selected\n");                 <--- Sigil was missing.

答案 1 :(得分:0)

您正在使用素数而不是素数:

foreach $a(@prime) {

你错过了listprimes for循环的结束括号。 (在退货声明之前)。

你是打印f而不是$ f:

print("f\n");

这应该使它&#34;工作&#34;,虽然它可能更清洁。

答案 2 :(得分:0)

编辑1

此修改基于您更新的帖子并列出了以下一些错误:

./listprime: line 3: use: command not found
./listprime: line 5: syntax error near unexpected token `('
./listprime: line 5: `my @primes =(2,3,5,7,11,13,17,19,23,29,31,37,41,43,47)'

产生这些错误是因为您似乎正在启动脚本,就像它是 shell 脚本而不是 Perl 脚本一样。例如:

➜  /tmp  zsh test.pl
test.pl:2: command not found: use
test.pl:4: command not found: 2,3,5,7,11,13,17,19,23,29,31,37,41,43,47
test.pl:4: command not found: my
test.pl:6: command not found: sub
test.pl:7: command not found: my
test.pl:11: parse error near `$a'

请注意,我的错误看起来不同,因为我使用的是Zsh,而你正在使用Bash,但它仍然是同样的问题。您应该使用 Perl 解释器,而不是这样做,如下所示:

➜  /tmp  perl test.pl
12

如果您的脚本已经可执行(使用chmod 755 <filename>添加执行权限),那么您可以将其作为./script.pl启动,并且第一行#!/usr/bin/perl行应该处理其余部分。

原始回复

这是我发现的代码问题的逐步解释。

需要的更改

您的代码有几个编译问题,甚至无法运行。使用命令perl -c <scriptfile>发出了几个问题,您可以重现这些问题,并且应该花时间去理解。

以下是listprimes功能的问题。请注意我在下面的代码中做出的评论以及我用来标记它们的!!-----标记:

sub listprimes {
        my $n = shift;

        my @answer = ();

        foreach $a (@primes) {   # !!----- the real array name is @primes, in plural
                if( $a<=$n ){ push @answer, $a; }
        }
        return @answer;   # !!---- This return goes outside the if block
}   # !!---- this brace was missing; you closed the loop's body, not the function's

简而言之,您引用了不存在的变量,缺少大括号和其他问题。同样,perl -c filename对您非常有帮助。

您最后的print("f\n");来电需要引用变量$f,因此它应为print("$f\n");

工作代码

!/usr/bin/perl
use strict;

my @primes =(2,3,5,7,11,13,17,19,23,29,31,37,41,43,47);

sub listprimes {
        my $n = shift;

        my @answer = ();

        foreach $a (@primes) {
                if( $a<=$n ){ push @answer, $a; }
        }
        return @answer;
}

sub random {
        my($a,$b) = @_;
        return int(rand($b-$a+1))+$a;
}

my $a = random(10, 50);
my $f = listprimes($a);

print("$f\n");

示例输出

➜  /tmp  ./test.pl
10

其他建议

您应该考虑为所有变量使用描述性的名称。诸如$a之类的变量名称不提供有关所述变量的内容的任何信息。例如,包含名称的数组@strings将更好地命名为@names(注意复数形式)。

具有多个“字词”的函数名称(例如listprimes)可以更好地读取为get_primeslist_primes。考虑到英语的Subject-Verb-Object结构,我倾向于更喜欢函数名的verb_object格式,因为它更自然地读取。换句话说,对于被认为是主题的任何给定脚本或模块,函数名get_primes读取的内容优于primes_get(除非您尝试像yoda一样说话,其他程序员不太可能欣赏)

在决定变量和函数的单数或复数名称时,应考虑类型。例如,标量变量只能包含单个值。因此,单数名称(例如$max_count)是合适的。另一方面,数组类型可以包含多个值,因此复数名称(例如@addresses)更合适。

这同样适用于功能。如果函数返回单个标量值,则使用单数名称(例如get_max_count)会很好,但如果它返回一个数组(例如get_addresses),那么复数它会更好。如果您始终如一地执行此操作,则可以向 代码的用户提供更多信息,这将是一个更好的地方:)