[英]New Perl user: using a hash of arrays
我正在做一个数据挖掘项目,其中一个perl脚本从SQL数据库中获取信息并进行解析。 数据由几个时间戳组成。 我想查找在任何特定日期存在多少种特定类型的时间戳。 不幸的是,这是我的第一个perl脚本,涉及哈希和数组时,perl的性质使我相当困惑。
代码段:
my %values=();#A hash of the total values of each type of data of each day.
#The key is the day, and each key stores an array of each of the values I need.
my @proposal;
#[drafted timestamp(0), submitted timestamp(1), attny approved timestamp(2),Organiziation approved timestamp(3), Other approval timestamp(4), Approved Timestamp(5)]
while(@proposal=$sqlresults->fetchrow_array()){
#TODO: check to make sure proposal is valid
#Increment the number of timestamps of each type on each particular date
my $i;
for($i=0;$i<=5;$i++)
$values{$proposal[$i]}[$i]++;
#Update rolling average of daily
#TODO: To check total load, increment total load on all dates between attourney approve date and accepted date
for($i=$proposal[1];$i<=$proposal[2];$i++)
$values{$i}[6]++;
}
我不断在for循环中增加值的语法错误。 另外,考虑到我正在使用严格警告,Perl在散列中访问它们时会自动创建正确值的数组,还是会遍地出界错误?
感谢您的帮助,扎克
错误:
for($i=0;$i<=5;$i++)
$values{$proposal[$i]}[$i]++;
for($i=$proposal[1];$i<=$proposal[2];$i++)
$values{$i}[6]++;
Perl不支持裸循环/条件块。 或更确切地说, 确实如此 ,但并非如此。 这可能在PHP中起作用,但在Perl中不起作用。 您将需要将它们包含在块中:
for($i=0;$i<=5;$i++) {
$values{$proposal[$i]}[$i]++;
}
for($i=$proposal[1];$i<=$proposal[2];$i++) {
$values{$i}[6]++;
}
$values{$proposal[$i]}[$i]++;
由于Perl中的哈希只能在其中容纳标量数据类型,因此为了将整个数组存储在哈希中,我们将不得不通过引用来实现。 这是有关数组引用的快速教程:
my $arr_ref = []; # empty array reference
my $arr_ref = [ 1, 2, 'foo', ]; # initialize with values
my $arr_ref = \@arr; # reference an existing array;
# does not make copy, but provides a
# read-write handle to the array
$arr_ref->[0]; # index the first (index 0) element of the array
@{$arr_ref}[ 0 .. 4 ]; # index elements number one through five (0-4) of the array
# through what's called an "array slice"
上面的代码所做的是从哈希%values
取出哈希键$proposal[$i]
的%values
,然后将其(标量)用作数组(不是数组)。
如前所述,您可以将其用作数组引用,但不能用作数组:
# v-- note the arrow
$values{$proposal[$i]}->[$i]++;
建议:
写my $foo; for ($foo = 0; $foo <= 5; $foo++)
my $foo; for ($foo = 0; $foo <= 5; $foo++)
更容易写为“ for my $foo (0 .. 5)
”或“ foreach my $foo (0 .. 5)
”。 本质上,这就是大多数人的做法。 值得注意的是for
和foreach
是可互换的–这是偏好和易读性的问题。
出于可读性考虑,请将代码缩进多个空格。 一个好的经验法则是四个空格或一个制表符。 St. Larry Wall在设计Perl时就想到了人们会说和写的语言。
我建议你研究的正确(正确的,在这里,意思是最有效的)的方式来写for
循环。 有迹象表明,可以加快程序的整体,如果他们有很多的长一些习惯for
循环。 例如:
++$foo
比$foo++
更有效。 这源于内部:
$foo++
递增变量,从中减去1,然后返回结果,而 ++$foo
递增变量并返回它。 更少的操作=更快。 for ($x=0; $x<=5; ++$x)
的书写方式与for ($x=0; $x<6; ++$x)
更好。 Perl有一些很棒的循环控件。 有些功能(例如map
)非常强大。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.