神秘的Perl语法错误?

时间:2018-04-11 01:45:04

标签: perl

我的Perl代码在注释行上引发了两个语法错误,但我无法解析这里的错误(我已经通过了几个工具)。我当然对Perl很陌生,但由于编译器非常不明确,我不知道出了什么问题。

while (<$file>)
 {  
#if(/(udp(\d*):\/\/)([^\s,]+|\d+\.\d+\.\d+\.\d+)(\sFace\sId:....\))?/)
    {
        $resolvable = $2;
        $output = $1.$2
        if(!exists $testedhash{"$resolvable"}){
            $testedhash{"$resolvable"} = 1;
            if($resolvable =~ /(\d+)\.(\d+)\.(\d+)\.(\d+)/)
            {
                my $temp = 255;
                if($1 gt $temp || $2 gt $temp || $3 gt $temp || $4 gt $temp)
                {
                    print "$_ is malformed\n"
                }
            }
            else
            {
                if($n->ping($resolvable))
                {
                    print "$output is up\n"
                }
                else
                {
                    print "$resolvable is down\n"
                }
            }
        }
    #}
 }

2 个答案:

答案 0 :(得分:2)

尝试跟踪语法错误时的经验法则是查看之前的行。

您的错误指向:

        if(!exists $testedhash{"$resolvable"}){

但实际上,这是错误的“结束” - perl确定存在问题的点。

它始于整个声明,它是其中的一部分。而且因为你错过了前一行的;,那就是“计算”了。

您的陈述实际上是:

    $output = $1.$2 if(!exists $testedhash{"$resolvable"}){

直到{有效 - 你可以根据帖子条件分配一个值。

但是,您真的想要包含在您的代码中:

  • use strict;
  • use warnings;
  • 如果您不确定错误 - use diagnostics;

您的代码中还有一些其他逻辑错误已在评论中注明 - 当您注释掉正则表达式时,$1$2无效。并且gt可能不是你想要的东西 - 它是一个字符串比较 - 所以“10”在“2”之前而不是像你期望的那样。

答案 1 :(得分:0)

所以不会真的奖励这个,等等等等,等等。但是我整理了你的代码并对我改变的内容提出了一些意见。我希望你觉得它很有帮助。

请注意,我实际上没有对此进行测试,因此我可以将其全部破坏。 YMMV,已知在实验室大鼠中引起癌症,4名牙医中有3名喜欢嚼口香糖。

use strict;    # Until you understand why you wouldn't want it, use strict.  It will save you a ton of errors.
use warnings;  # Same with warnings.

# Break up your regexes into labeled pieces
# It makes them easier to understand.
my $UDP_DATA = qr{udp\d*://};
my $HOST_NAME = qr/[^\s,]+/;
my $HOST_IP4_ADDRESS = qr/\d+\(?.\d+){3}/;
my $SOME_STUFF = qr/Face\sId:..../;


my $n = SomeKindOfPinger->new();

while (defined my $line = <$file>) {

    # Use early returns and loop continuation to avoid deep nesting.
    # Extended regexes let you use space and comments in regexes to make them even easier to read.
    next unless $line =~ m{
            ( $UDP_DATA )
            (   $HOST_IP4_ADDRESS
              | $HOST_NAME
            )
            \s $SOME_STUFF
        }x;

    # Use better variable names, output could be anything.
    # we don't know if resolvable is resolvable at this point, so it's just a host.
    my $label = "$1$2";
    my $host = $2;

    # Bail out avoids nesting again.
    # Variable names with types in them like "some_hash" or "monkey_array" are a code smell.
    next if exists $tested_hosts{$host};

    $tested_hosts{$host}++;

    # We got to reuse that regex piece. Handy.
    if ( $host =~ $HOST_IP4_ADDRESS ) {
        # If you have a bunch of checks to do, put them in a data structure and iterate
        my @octets = split /\./, $host;
        my @bad = grep $_>255, @octets; # grep is like JS 'filter' function.
                                        # This says: "Show me the malformed octets."

        # An array, like @bad, in scalar context to the number of items in the array.
        # So it returns 0 or FALSE if it is empty.
        # So if any octets are malformed, we print the message.
        print "$line is malformed\n"
            if @bad;
    }
    else {
        # if you are doing the same kind of operation, no matter how an if/else chain goes,
        # just with different data, use a ternary operator.
        # Here, we print no matter what.
        # So if ping is true, we print the happy message. Otherwise we print the sad message.
        print $n->ping($host)
            ? "$label is up\n"
            : "$label is busted\n";
    }
}