2016-03-21 51 views
0

背景:使用字符串EQ未初始化值的27

我不是一个PERL专家,但在迁移一些脚本到新的服务器使用Perl的新版本和PHP所有的工作其他人工作,但这个特定的一个不工作。

我已经安装了这个脚本依赖运行的所有模块,并且这些PM相关的错误已经停止。

环境:

  • Web服务器运行
  • 的Ubuntu 12.04 LTS 64位
  • 的Apache 2
  • Mysql的
  • PHP5
  • freetds的
  • 所有防火墙许可,远程数据库连接 测试和验证
  • 所有必需的Perl模块和Apache/PHP5 扩展测试和验证

脚本功能:

脚本是为了从RSS拉故事,并把它们到远程数据库。

问题:

在脚本这个新的服务器我得到下面的错误上没有问题,运行旧的服务器:

Use of uninitialized value in string eq at ./parse_rss.pl line 27.

第27行是这样的:

if (ref($item->{'company:symbol'} eq 'ARRAY')) { 
       next; 

请在下面查看完整的脚本:

#!/usr/bin/perl 
# 

use warnings; 
use strict; 
use DateTime; 
use DateTime::Format::ISO8601; 
use XML::FeedPP; 

my $starttime; 
if ($#ARGV == -1) { 
     $starttime = DateTime::Format::ISO8601->parse_datetime("1970-01-01T00:00:00"); 
} 
else { 
     $starttime = DateTime::Format::ISO8601->parse_datetime($ARGV[0]); 
} 

my $feed = XML::FeedPP->new("http://RSS.FEED.URL"); 
my $num_items = $feed->get_item(); 
for (my $i = $num_items - 1; $i >= 0; $i--) 
{ 
     my $item = $feed->get_item($i); 
     my $dt = DateTime::Format::ISO8601->parse_datetime($item->pubDate); 
     if ($dt < $starttime) { 
       last; 
     } 
     if (ref($item->{'company:symbol'} eq 'ARRAY')) { 
       next; 
     } 
     if ($item->title =~ /(.+?) (upgraded|downgraded) to (.+?) from (.+?) at (.+)/) { 
       print sprintf("%04d-%02d-%02d %02d:%02d:%02d", $dt->year(), $dt->month(), $dt->day(), $dt->hour(), $dt->minute(), $dt->second()) . "|$1|" . $item->{'company:symbol'} . "|$2|$3|$4|$5\n"; 
     } 
     elsif ($item->title =~ /(.+?) (initiated) with (\w+) (.+?) at (.+)/) { 
       print sprintf("%04d-%02d-%02d %02d:%02d:%02d", $dt->year(), $dt->month(), $dt->day(), $dt->hour(), $dt->minute(), $dt->second()) . "|$1|" . $item->{'company:symbol'} . "|$2|$4|...None...|$5\n"; 
     } 
} 

任何帮助,将不胜感激

+0

什么是'$项的值'?您可以使用['Data :: Dumper'](https://metacpan.org/pod/Data::Dumper)轻松打印散列 –

+3

这些括号肯定是错误的。 'ref($ foo eq“bar”)'将始终返回一个空字符串,因为'eq'的结果永远不会是引用。 – ThisSuitIsBlackNot

回答

0

你的括号是在错误的地方

if (ref($item->{'company:symbol'} eq 'ARRAY')) { 

应该

if (ref($item->{'company:symbol'}) eq 'ARRAY') { 

ref返回一个字符串,这在阵列的情况恰好是ARRAY。因此,这将检查该散列元素中的引用是否是数组引用。

0

由于TLP says,问题是你的线

if (ref($item->{'company:symbol'} eq 'ARRAY')) 

表达$item->{'company:symbol'} eq 'ARRAY'计算结果为真正 -1或空字符串和ref运算符返回false,空字符串 - 在这两种情况下,因为既不是参考

您的意思是检查散列元素是否是数组引用,所以

if (ref $item->{'company:symbol'} eq 'ARRAY') 

没有括号都将将罚款

有一些与你的代码的其他问题。具体来说,我认为在循环开始时提取迭代值的函数是更合适的。

所以,举例来说

if (ref($item->{'company:symbol'} eq 'ARRAY')) { 
    next; 
} 

更清晰写成

my $company_symbol = $item->{'company:symbol'}; 

next if ref $company_symbol eq 'ARRAY'; 

这是你的代码的版本,您可能更喜欢

#!/usr/bin/perl 

use warnings; 
use strict; 

use DateTime; 
use DateTime::Format::ISO8601; 
use XML::FeedPP; 

my $starttime; 

if (@ARGV) { 
    $starttime = DateTime::Format::ISO8601->parse_datetime($ARGV[0]); 
} 
else { 
    $starttime = DateTime::Format::ISO8601->parse_datetime('1970-01-01T00:00:00'); 
} 

my $feed  = XML::FeedPP->new('http://rss.feed.url'); 
my $num_items = $feed->get_item; 

for (my $i = $num_items - 1; $i >= 0; --$i) { 

    my $item   = $feed->get_item($i); 
    my $company_symbol = $item->{'company:symbol'}; 
    my $pub_date  = DateTime::Format::ISO8601->parse_datetime($item->pubDate); 
    my $title   = $item->title; 

    last if $pub_date < $starttime; 

    next if ref $company_symbol eq 'ARRAY'; 

    if ($title =~ /(.+?) (upgraded|downgraded) to (.+?) from (.+?) at (.+)/) { 

     print join('|', 
      $pub_date->strftime('%Y-%m-%d %h:%m:%s'), 
      $1, 
      $company_symbol, 
      $2, 
      $3, 
      $4, 
      $5 
     ), "\n"; 
    } 
    elsif ($title =~ /(.+?) (initiated) with (\w+) (.+?) at (.+)/) { 

     print join('|', 
      $pub_date->strftime('%Y-%m-%d %h:%m:%s'), 
      $1, 
      $company_symbol, 
      $2, 
      $4, 
      '...None...', 
      $5 
     ), "\n"; 
    } 
}