简体   繁体   English

Perl排序哈希,如何按$ hash排序{$ key} - > {secondkey}

[英]Perl sort hash, how to sort by $hash{$key}->{secondkey}

I have a Perl function: 我有一个Perl函数:

my %d;

$d{"aaaa"}->{t1} = "9:49";
$d{"bbbb"}->{t1} = "9:30";

foreach my $k (sort { ($d{$a}->{t1}) <=> ($d{$b}->{t1}) } keys %d)
{
    print "$k:  $d{$k}->{t1}\n";
}

I want to sort by t1, so 9:30 before 9:49 and I want to get the result: 我想按t1排序,所以在9:49之前9:30我想得到结果:

bbbb:  9:30
aaaa:  9:49

but the result is not suitable. 但结果不合适。

It seems like the result is random? 似乎结果是随机的?

C:\tmp>a.pl
bbbb:  9:30
aaaa:  9:49

C:\tmp>a.pl
bbbb:  9:30
aaaa:  9:49

C:\tmp>a.pl
bbbb:  9:30
aaaa:  9:49

C:\tmp>a.pl
aaaa:  9:49
bbbb:  9:30

C:\tmp>a.pl
bbbb:  9:30
aaaa:  9:49

C:\tmp>a.pl
bbbb:  9:30
aaaa:  9:49

C:\tmp>a.pl
bbbb:  9:30
aaaa:  9:49

C:\tmp>a.pl
aaaa:  9:49
bbbb:  9:30

在此输入图像描述

You need to use cmp instead of <=> since you are comparing strings. 您需要使用cmp而不是<=>因为您正在比较字符串。 The comments are correct and we need to take into consideration 10+ hours. 评论是正确的,我们需要考虑10个多小时。 You need to use sprintf to add leading zero when hours are less than 10 to have strings sorted correctly. 当小时数小于10时,您需要使用sprintf添加前导零,以正确排序字符串。

foreach my $k (sort { sprintf("%05s", ($d{$a}->{t1})) cmp sprintf("%05s", ($d{$b}->{t1})) } keys %d) {

<=> is for comparing numbers, but your times have a colon, which makes them strings instead of numbers. <=>用于比较数字,但你的时间有一个冒号,这使得它们成为字符串而不是数字。 One workaround is to just remove the colon, so that <=> can operate on them in number context. 一种解决方法是只删除冒号,以便<=>可以在数字上下文中对它们进行操作。

use v5.10;

say "$_: $d{$_}->{t1}" for sort { $d{$a}->{t1} =~ s/://r <=> $d{$b}->{t1} =~ s/://r } keys %d;

The r modifier on the substitution means return the new value without altering the old value. 替换上的r修饰符意味着返回新值而不更改旧值。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM