Perl:按数字顺序强制散列
Perl: Force hash in numeric order
我正在尝试按记录编号顺序显示散列数据(即按散列键排序)。我已将记录存储在具有相关记录编号的哈希中。
我做错了什么?
下面是显示问题的一些类似代码
#!/usr/bin/env perl
use strict;
use Time::HiRes;
my $rec = {};
my %Data;
my $recno = 1;
while ($recno <= 100) {
$rec->{recno} = $recno;
$rec->{dt} = qx/date/;
$Data{ $rec->{recno} } = $rec;
# Initialize
Time::HiRes::sleep(0.2);
$recno++;
$rec = {};
}
my $count = keys %Data;
print "Found $count records\n";
foreach my $rec (sort { $Data{$a} <=> $Data{$b} } keys %Data) {
#foreach my $rec (sort { $Data{$a} cmp $Data{$b} } keys %Data) {
print " Rec No: --".$rec."--\n";
print " Date: ". $Data{$rec}{dt}."\n";
}
有时它会按顺序显示哈希值,有时则不会。跟记录数有点关系的样子。
Found 100 records
Rec No: --1--
Date: Thu Feb 13 15:19:46 UTC 2020
Rec No: --31--
Date: Thu Feb 13 15:19:52 UTC 2020
Rec No: --32--
Date: Thu Feb 13 15:19:52 UTC 2020
Rec No: --33--
Date: Thu Feb 13 15:19:52 UTC 2020
Rec No: --34--
Date: Thu Feb 13 15:19:52 UTC 2020
Rec No: --35--
Date: Thu Feb 13 15:19:52 UTC 2020
Rec No: --36--
Date: Thu Feb 13 15:19:53 UTC 2020
您正在比较值,但需要比较键:
for my $rec (sort { $a <=> $b } keys %Data) {
请参阅@choroba 的回答以解决您所说的问题。
但是为了让问题一开始就不会出现,为任务选择最佳数据结构。在这种情况下,你需要一个数组,而不是散列。我还使用了更具描述性的变量名称和小写标识符(参见 Conway (2005))。
#!/usr/bin/env perl
use warnings;
use strict;
use Time::HiRes;
my $delay = 0.2;
my $num_dates = 100;
my @dates;
for ( 0 .. ($num_dates - 1) ) {
chomp( my $date = `date` );
push @dates, $date;
Time::HiRes::sleep($delay);
}
for ( 0..$#dates ) {
print join( "\t", $_, $dates[$_] ), "\n";
}
参考:
达米安康威。 (2005) Perl 最佳实践:开发可维护代码的标准和样式。奥莱利媒体:http://shop.oreilly.com/product/9780596001735.do
稍微更正的代码产生了预期的结果。
注意:Windows 中的 date
需要选项 /T
否则它会等待用户输入
use strict;
use warnings;
use feature 'say';
use Time::HiRes;
my $debug = 0; # debug flag
my %Data;
my($rec_id,$record); # declared here for format
my $num_records = 100; # define number of records
foreach my $recno (1..$num_records) {
say "Record: $recno" if $debug;
my $rec = {};
$rec->{recno} = $recno;
$rec->{dt} = qx/date \/T/; # /T required for Windows
$Data{ $rec->{recno} } = $rec;
# Initialize
Time::HiRes::sleep(0.2);
$recno++;
$rec = {};
}
my $count = keys %Data;
say "Total $count records";
$~ = 'STDOUT_HEAD';
write;
$~ = 'STDOUT';
foreach $rec_id (sort { $a <=> $b } keys %Data) {
$record = $Data{$rec_id}{dt};
write;
}
$~ = 'STDOUT_BOTTOM';
write;
format STDOUT_HEAD =
+------+------------------------------+
| No. | Record |
+------+------------------------------+
.
format STDOUT =
| @>>> | @<<<<<<<<<<<<<<<<<<<<<<<<<<< |
$rec_id, $record
.
format STDOUT_BOTTOM =
+------+------------------------------+
.
输出
Total 100 records
+------+------------------------------+
| No. | Record |
+------+------------------------------+
| 1 | Thu 02/13/2020 |
| 2 | Thu 02/13/2020 |
| 3 | Thu 02/13/2020 |
| 4 | Thu 02/13/2020 |
| 5 | Thu 02/13/2020 |
| 6 | Thu 02/13/2020 |
| 7 | Thu 02/13/2020 |
| 8 | Thu 02/13/2020 |
| 9 | Thu 02/13/2020 |
| 10 | Thu 02/13/2020 |
.......................................
.......................................
| 95 | Thu 02/13/2020 |
| 96 | Thu 02/13/2020 |
| 97 | Thu 02/13/2020 |
| 98 | Thu 02/13/2020 |
| 99 | Thu 02/13/2020 |
| 100 | Thu 02/13/2020 |
+------+------------------------------+
我正在尝试按记录编号顺序显示散列数据(即按散列键排序)。我已将记录存储在具有相关记录编号的哈希中。
我做错了什么?
下面是显示问题的一些类似代码
#!/usr/bin/env perl
use strict;
use Time::HiRes;
my $rec = {};
my %Data;
my $recno = 1;
while ($recno <= 100) {
$rec->{recno} = $recno;
$rec->{dt} = qx/date/;
$Data{ $rec->{recno} } = $rec;
# Initialize
Time::HiRes::sleep(0.2);
$recno++;
$rec = {};
}
my $count = keys %Data;
print "Found $count records\n";
foreach my $rec (sort { $Data{$a} <=> $Data{$b} } keys %Data) {
#foreach my $rec (sort { $Data{$a} cmp $Data{$b} } keys %Data) {
print " Rec No: --".$rec."--\n";
print " Date: ". $Data{$rec}{dt}."\n";
}
有时它会按顺序显示哈希值,有时则不会。跟记录数有点关系的样子。
Found 100 records
Rec No: --1--
Date: Thu Feb 13 15:19:46 UTC 2020
Rec No: --31--
Date: Thu Feb 13 15:19:52 UTC 2020
Rec No: --32--
Date: Thu Feb 13 15:19:52 UTC 2020
Rec No: --33--
Date: Thu Feb 13 15:19:52 UTC 2020
Rec No: --34--
Date: Thu Feb 13 15:19:52 UTC 2020
Rec No: --35--
Date: Thu Feb 13 15:19:52 UTC 2020
Rec No: --36--
Date: Thu Feb 13 15:19:53 UTC 2020
您正在比较值,但需要比较键:
for my $rec (sort { $a <=> $b } keys %Data) {
请参阅@choroba 的回答以解决您所说的问题。
但是为了让问题一开始就不会出现,为任务选择最佳数据结构。在这种情况下,你需要一个数组,而不是散列。我还使用了更具描述性的变量名称和小写标识符(参见 Conway (2005))。
#!/usr/bin/env perl
use warnings;
use strict;
use Time::HiRes;
my $delay = 0.2;
my $num_dates = 100;
my @dates;
for ( 0 .. ($num_dates - 1) ) {
chomp( my $date = `date` );
push @dates, $date;
Time::HiRes::sleep($delay);
}
for ( 0..$#dates ) {
print join( "\t", $_, $dates[$_] ), "\n";
}
参考:
达米安康威。 (2005) Perl 最佳实践:开发可维护代码的标准和样式。奥莱利媒体:http://shop.oreilly.com/product/9780596001735.do
稍微更正的代码产生了预期的结果。
注意:Windows 中的 date
需要选项 /T
否则它会等待用户输入
use strict;
use warnings;
use feature 'say';
use Time::HiRes;
my $debug = 0; # debug flag
my %Data;
my($rec_id,$record); # declared here for format
my $num_records = 100; # define number of records
foreach my $recno (1..$num_records) {
say "Record: $recno" if $debug;
my $rec = {};
$rec->{recno} = $recno;
$rec->{dt} = qx/date \/T/; # /T required for Windows
$Data{ $rec->{recno} } = $rec;
# Initialize
Time::HiRes::sleep(0.2);
$recno++;
$rec = {};
}
my $count = keys %Data;
say "Total $count records";
$~ = 'STDOUT_HEAD';
write;
$~ = 'STDOUT';
foreach $rec_id (sort { $a <=> $b } keys %Data) {
$record = $Data{$rec_id}{dt};
write;
}
$~ = 'STDOUT_BOTTOM';
write;
format STDOUT_HEAD =
+------+------------------------------+
| No. | Record |
+------+------------------------------+
.
format STDOUT =
| @>>> | @<<<<<<<<<<<<<<<<<<<<<<<<<<< |
$rec_id, $record
.
format STDOUT_BOTTOM =
+------+------------------------------+
.
输出
Total 100 records
+------+------------------------------+
| No. | Record |
+------+------------------------------+
| 1 | Thu 02/13/2020 |
| 2 | Thu 02/13/2020 |
| 3 | Thu 02/13/2020 |
| 4 | Thu 02/13/2020 |
| 5 | Thu 02/13/2020 |
| 6 | Thu 02/13/2020 |
| 7 | Thu 02/13/2020 |
| 8 | Thu 02/13/2020 |
| 9 | Thu 02/13/2020 |
| 10 | Thu 02/13/2020 |
.......................................
.......................................
| 95 | Thu 02/13/2020 |
| 96 | Thu 02/13/2020 |
| 97 | Thu 02/13/2020 |
| 98 | Thu 02/13/2020 |
| 99 | Thu 02/13/2020 |
| 100 | Thu 02/13/2020 |
+------+------------------------------+