我有一个从文件中收集的哈希值。下面的脚本将按预期打印所有值(注意我只包含脚本的重要部分,因此打开输入文件时不会添加太宽):
use strict;
use warnings;
my %hash = ();
while (<$fh>) {
my ($region, $site, $layer) = split;
push @{$hash{$region}}, "$region $site $layer";
}
foreach my $values(keys %hash) {
print $values,"\n";
}
我的问题是,我不想根据键打印所有值,我实际上想要分解值并通过告诉perl我想要的东西在不同区域打印它们,而不仅仅是打印{{1 }}
例如,如果我有以下数据:
$values
我实际上希望能够在其他区域使用这些值,并打印如下内容:
North belair layer2
North belair layer3
East Monte layer2
East Vista layer3
将打印:
belair有图层:layer2 layer3
Monte有图层:layer2
Vista有图层:layer3
或
print "$site has layers: $layer"
然后将打印:
North有站点:belair和layers:layer2 layer3
East有网站:Monte Vista和图层:layer2 layer3
当我运行多个print "$region has sites, $site and $site has layers: $layer";
循环时,我得到重复的结果,我不知道要转到哪个方向。我所做的每项搜索都只向我展示了如何为foreach
$values
答案 0 :(得分:3)
对于直接问题:迭代键并将每个值拆分为变量
foeach my $region (sort keys %hash) {
my ($region, $site, $layer) = split ' ', $region;
...
}
然后您可以使用它进行首次打印。
然而,有两个笔记是有序的。
为什么$region
是键的一部分?相反,为什么不
...
push @{$hash{$region}}, "$site $layer";
以便您将网站和图层与区域相关联。
更重要的是,区域中的条目具有相同的站点,并且您显然需要区域内站点的所有层。那么你可能想要一个嵌套结构
%hash = ( region => { site => [ layer, ... ], ... }, ... )
可以填充
while (<$fh>) {
my ($region, $site, $layer) = split;
push @{$hash{$region}->{$site}}, $layer;
}
通过这种方式,您可以对区域内的所有图层进行第二次打印
foreach my $region (sort keys %hash) {
print "$region has sites: ",
join(' and ', keys %{$hash{$region}}), ", with layers: ";
foreach my $site (keys %{$hash{$region}}) {
print "@{$hash{$region}->{$site}} "
}
say '';
}
打印什么
East has sites: Vista and Monte, with layers: layer3 layer2 North has sites: belair, with layers: layer2 layer3
答案 1 :(得分:3)
my %sites;
my %regions;
while (<>) {
my ($region_id, $site_id, $layer_id) = split;
# Use hashes instead of arrays to remove duplicates.
++$sites{$site_id}{layers}{$layer_id};
++$regions{$region_id}{layers}{$layer_id};
++$regions{$region_id}{sites}{$site_id};
}
# "Flatten" hashes into sorted arrays of unique elements.
for my $site_id (keys(%sites)) {
my $site = $sites{$site_id};
$site->{layers} = [ sort keys(%{ $site->{layers} }) ];
}
for my $region_id (keys(%regions)) {
my $region = $regions{$region_id};
$region->{layers} = [ sort keys(%{ $region->{layers} }) ];
$region->{sites} = [ sort keys(%{ $region->{sites} }) ];
}
# Now do what we want to do.
for my $site_id (sort keys(%sites)) {
my $site = $sites{$site_id};
print "$site_id has layers @{ $site->{layers} }\n";
}
for my $region_id (sort keys(%regions)) {
my $region = $regions{$region_id};
print "$region_id has sites @{ $region->{sites} } and layers @{ $region->{layers} }\n";
}