如何自然地对哈希键进行排序?

发布于 2024-07-10 19:40:15 字数 263 浏览 8 评论 0原文

我有一个 Perl 哈希,其键以数字开头或为数字。

如果我使用,

foreach my $key (sort keys %hash) {
    print $hash{$key} . "\n";
}

列表可能会显示为,

0
0001
1000
203
23

而不是

0
0001
23
203
1000

I have a Perl hash whose keys start with, or are, numbers.

If I use,

foreach my $key (sort keys %hash) {
    print $hash{$key} . "\n";
}

the list might come out as,

0
0001
1000
203
23

Instead of

0
0001
23
203
1000

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(4

蓝海似她心 2024-07-17 19:40:15
foreach my $key (sort { $a <=> $b} keys %hash) {
    print $hash{$key} . "\n";
}

排序操作采用可选的比较“子例程”(或者作为代码块,就像我在这里所做的那样,或者作为子例程的名称)。 我提供了一个内联比较,使用内置数字比较运算符“<=>”将键视为数字。

foreach my $key (sort { $a <=> $b} keys %hash) {
    print $hash{$key} . "\n";
}

The sort operation takes an optional comparison "subroutine" (either as a block of code, as I've done here, or the name of a subroutine). I've supplied an in-line comparison that treats the keys as numbers using the built-in numeric comparison operator '<=>'.

樱桃奶球 2024-07-17 19:40:15

Paul 的答案对于数字来说是正确的,但是如果您想更进一步,像人类一样对混合单词和数字进行排序,那么 cmp<=> 都不会。 例如,

  9x
  14
  foo
  fooa
  foolio
  Foolio
  foo12
  foo12a
  Foo12a
  foo12z
  foo13a

Sort::Naturally 可以解决这个问题,提供 nsortncmp 例程。

Paul's answer is correct for numbers, but if you want to take it a step further and sort mixed words and numbers like a human would, neither cmp nor <=> will do. For example,

  9x
  14
  foo
  fooa
  foolio
  Foolio
  foo12
  foo12a
  Foo12a
  foo12z
  foo13a

Sort::Naturally takes care of this problem, providing the nsort and ncmp routines.

蛮可爱 2024-07-17 19:40:15

您的第一个问题是循环体(这里似乎没有其他答案指出)。

foreach my $key ( sort keys %hash ) {
    print $hash{$key} . "\n";
}

我们不知道 %hash 的键是什么。 我们只知道它们在循环内以 $key 的形式按照词汇顺序传递给您。 然后,您可以使用密钥访问哈希的内容,并打印每个条目。

散列的不会按排序顺序出现,因为您是按排序的。

您是否想按排序顺序输出,请考虑以下循环:

foreach my $value ( sort values(%hash) ) {
    printf( "%s\n", $value );
}

此循环确实按照您观察到的顺序打印值:

0
0001
1000
203
23

要按数字对它们进行排序,请使用

foreach my $value ( sort { $a <=> $b } values(%hash) ) {
    printf( "%s\n", $value );
}

这会产生

0
0001
23
203
1000

您想要的结果。

有关详细信息,请参阅sort 函数的 Perl 手册还有更多的例子。

Your first problem is the body of the loop (which no other answer here seems to point out).

foreach my $key ( sort keys %hash ) {
    print $hash{$key} . "\n";
}

We don't know what the keys of %hash are. We just know that they that are handed to you as $key, in lexical order, inside the loop. You then use the keys to access the contents of the hash, printing each entry.

The values of the hash do not come out in a sorted order, because you sort on the keys.

Would you instead want to output the values in sorted order, consider the following loop:

foreach my $value ( sort values(%hash) ) {
    printf( "%s\n", $value );
}

This loop does print the values in the order you observe:

0
0001
1000
203
23

To sort them numerically instead, use

foreach my $value ( sort { $a <=> $b } values(%hash) ) {
    printf( "%s\n", $value );
}

This produces

0
0001
23
203
1000

which is what you wanted.

See the Perl manual for the sort function for further information and many more examples.

简单气质女生网名 2024-07-17 19:40:15
$key (sort { $a <=> $b} keys %hash) 

就可以了

或者降序排序:

$key (sort { $b <=> $a} keys %hash)

或者甚至

$key (sort { $a <=> $b} values %hash)
$key (sort { $b <=> $a} values %hash)
$key (sort { $a <=> $b} keys %hash) 

will do the trick

Or descending sort:

$key (sort { $b <=> $a} keys %hash)

Or even

$key (sort { $a <=> $b} values %hash)
$key (sort { $b <=> $a} values %hash)
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文