返回具有最大值的所有散列键/值对

时间:2011-05-11 01:54:26

标签: perl hash

我有一个哈希(在Perl中),其中值都是数字。我需要创建另一个散列,其中包含来自第一个散列的所有键/值对,其中值是所有值的最大值。

例如,给定

my %hash = (
    key1 => 2,
    key2 => 6,
    key3 => 6,
);

我想创建一个包含以下内容的新哈希:

%hash_max = (
    key2 => 6,
    key3 => 6,
);

我确信有很多方法可以做到这一点,但我正在寻找一个优雅的解决方案(并有机会学习!)。

3 个答案:

答案 0 :(得分:7)

use List::Util 'max';
my $max = max(values %hash);
my %hash_max = map { $hash{$_}==$max ? ($_, $max) : () } keys %hash;

或一次通过方法(与另一个答案类似但略有不同):

my $max;
my %hash_max;
keys %hash; # reset iterator
while (my ($key, $value) = each %hash) {
    if ( !defined $max || $value > $max ) {
        %hash_max = ();
        $max = $value;
    }
    $hash_max{$key} = $value if $max == $value;
}

答案 1 :(得分:1)

这使得一次传递数据,但浪费了大量的哈希写入:

use strict;
use warnings;

my %hash = (
    key1 => 2,
    key2 => 6,
    key3 => 6,
);

my %hash_max = ();
my $max;
foreach my $key (keys %hash) {
        if (!defined($max) || $max < $hash{$key} ) {
                %hash_max = ();
                $max = $hash{$key};
                $hash_max{$key} = $hash{$key};
        }
        elsif ($max == $hash{$key}) {
                $hash_max{$key} = $hash{$key};
        }
}

foreach my $key (keys %hash_max) {
        print "$key\t$hash_max{$key}\n";
}

答案 2 :(得分:1)

# sort numerically descending
my @topkey = sort {$hash{$b} <=> $hash{$a}} keys %hash;

然后将最高值复制到%hash_max,并在最后一个最大值之后使用循环终止符:

for $key (@topkey) {
    if ($hash{$key} == $hash{$topkey[0]}) {
        $hash_max{$key} = $hash{$key}
    } else { last }
}

ETA:请注意,last因为@topkey中的键已排序而对{{1}}起作用,所以当值不再像第一个那样时,我们可以打破循环。即以下所有值都较低。