perl中的加权排序?

时间:2013-07-01 14:07:47

标签: perl sorting weighted

我有一个散列哈希,其值都是数值。我可以使用sort命令排序和/或按顺序排序哈希值,但是如果我想对结果进行加权而不是按照指定的键顺序排序呢?有没有办法做到这一点?

编辑:好的,这是代码......

my @check_order = ["disk_usage","num_dbs","qps_avg"];
my %weights     = ( disk_usage => .7,
                    num_dbs    => .4,
                    qps_avg    => .2
);
my @dbs=sort { 
    ($stats{$a}->{$check_order[0]}*$weights{$check_order[0]}) <=>
    ($stats{$b}->{$check_order[0]}*$weights{$check_order[0]})  or
    ($stats{$a}->{$check_order[1]}*$weights{$check_order[1]}) <=> 
    ($stats{$b}->{$check_order[1]}*$weights{$check_order[1]}) or
    ($stats{$a}->{$check_order[2]}*$weights{$check_order[2]}) <=> 
    ($stats{$b}->{$check_order[2]}*$weights{$check_order[2]})
} keys(%stats);

2 个答案:

答案 0 :(得分:1)

您希望根据每个元素的函数值对列表进行排序。因此,请在sort语句中使用函数。

@sorted = sub { sort_function($a) <=> sort_function($b) } @unsorted;

sub sort_function {
    my ($input) = @_;

    return $input->{disk_usage} * 0.7 
         + $input->{num_dbs} * 0.4 
         + $input->{qps_avg} * 0.2;

    # -or- more generally

    my $value = 0;
    while (my ($key,$weight) = each %weights) {
        $value += $input->{$key} * $weight;
    }
    return $value;
}

当您的排序功能很昂贵并且要排序的项目很多时,Schwartzian transform可以提高您的排序效果:

@sorted = map { $_->[0] }
          sort { $a->[1] <=> $b->[1] }
          map { [ $_, sort_function($_) ] } 
          @unsorted;

答案 1 :(得分:0)

如果您的权重存储在另一个哈希%property中 这将根据产品$hash{key} * $property{key}

对哈希键进行排序
#!/usr/bin/perl
use strict;
use warnings;

my %hash = (
  a => 51,
  b => 61,
  c => 71,
);

my %property = ( a => 7, b => 6, c => 5 );


foreach (sort { ($hash{$a}*$property{$a}) <=> 
                ($hash{$b}*$property{$b}) } keys %hash)
{
    printf("[%d][%d][%d]\n",
    $hash{$_},$property{$_},$hash{$_}*$property{$_});
}