0

我有一个看起来像这样的数据

#Status value
TP       5.000
TP       3.000
TP       3.000
TN       10.000
TP       2.000
TP       9.000
TN       1.000
TP       9.000
TN       1.000

我们要做的是根据给定的时间间隔对状态进行聚类value。让该间隔为1-3, 4-6, 7-9, 10-12, etc ..(即 Bin 大小 3)。

我们希望得到这样的数组哈希:

my %hoa = (
'1-3' => [TP,TP,TP,TN,TN],
'4-6' => [TP],
'7-9' => [TP,TP],
'10-12' => [TN]);

实现这一目标的方法是什么?

更新:更正了 HoA 7-9,感谢 ysth。

4

2 回答 2

2

抽象出代码以确定间隔:

sub interval {
    my ($val) = @_;
    my $i = int( ( $val + 2 ) / 3 );
    my $interval = sprintf( '%d-%d', $i * 3 -2, $i * 3 );
    return $interval;
}

my %hoa;
while ( my $line = <> ) {
    next if $line =~ /^#/;
    my ($status, $value) = split ' ', $line;
    push @{ $hoa{ interval($value) } }, $status;
}

use Data::Dumper;
print Dumper \%hoa;

(它为 7-9 获得两个 TP,而不是您显示的一个)。

于 2010-11-08T03:35:23.477 回答
2

ysth 的回答也是我想到的第一件事,我认为他的方法是正确的。

我只想提出一个建议:您可以使用聚类算法以一种面向未来的方式为您执行此操作(例如,当您的数据变为多维时)。例如,K-means可以正常工作,即使对于像您这样的一维数据也是如此。

例如:

use strict; use warnings;
use Algorithm::KMeans;

my $datafile = $ARGV[0] or die;
my $K        = $ARGV[1] or 0;
my $mask     = 'N1';

my $clusterer = Algorithm::KMeans->new(
    datafile => $datafile,
    mask     => $mask,
    K        => $K,
    terminal_output => 0,
);

$clusterer->read_data_from_file();

my ($clusters, $cluster_centers) = $clusterer->kmeans();

my %clusters;

while (@$clusters) {

    my $cluster = shift @$clusters;
    my $center  = shift @$cluster_centers;

    $clusters{"@$center"} = $cluster;
}

use YAML; print Dump \%clusters;
于 2010-11-08T06:57:33.340 回答