2

文件星期一.csv

223.22;1256.4
227.08;1244.8
228.08;1244.7
229.13;1255.0
227.89;1243.2
224.77;1277.8

文件星期二.csv

227.02;1266.3
227.09;1234.9
225.18;1244.7
224.13;1255.3
228.59;1263.2
224.70;1247.6

这个 Perl 单行器从文件“monday.csv”中的第一列中前三位是 227 或 226 的行中为我提供了第二列中具有最高值的行:

perl -F\; -ane '$hash{$_} = $F[1] if /22[78]/; END{ print and exit for sort{ $hash{$b} <=> $hash{$a} } keys %hash }' monday.csv

这个 Perl 单行器为我提供了第二列中第二列中值最高的行,其中第一列中的前 3 位数字是所有 *day.csv 文件中的 227 或 226:

perl -F\; -ane '$hash{$_} = $F[1] if /22[78]/; END{ print and exit for sort{ $hash{$b} <=> $hash{$a} } keys %hash }' *day.csv

我怎么能重写这个单行以获得类似的输出

文件名:“文件'filename.csv'中第一列前3位数字为227或226的行中第二列中具有最高值的行”

每个*day.csv文件?

4

3 回答 3

5

您可以使用$ARGV当前文件名。如果您只对最大值感兴趣,则无需存储所有值然后对其进行排序;相反,只需存储每个文件的最大值。此外,您的正则表达式可能应该锚定到行首。

# Line breaks added for display purposes.
perl -F\; -ane '
    $max{$ARGV} = $F[1] if /^22[78]/ and $F[1] > $max{$ARGV};
    END{ print "$_\t$max{$_}" for sort keys %max}
' *day.csv

或者,如果您想存储最大值出现的整行:

perl -F\; -ane '
    ($max{$ARGV}{ln}, $max{$ARGV}{mx}) = ($_, $F[1])
        if /^22[78]/ and $F[1] > $max{$ARGV}{mx};
    END{ print "$_\t$max{$_}{ln}" for sort keys %max}
' *day.csv
于 2010-10-16T10:12:52.723 回答
2

文件名包含在$ARGV变量中:

$ARGV

从 <> 读取时包含当前文件的名称。


但是,所提出的单线有一个问题。如果您的第一列有重复值怎么办?

一个更好的单线将是:

$ perl -F/;/ -MList::Util=max -lane 'push @{ $wanted{$ARGV} }, $F[1] if $F[0] =~ /22[78]/; } END { print "$ARGV : ", max(@{ $wanted{$_} }) for keys %wanted;' *.csv

根据评论:

$ perl -F/;/ -lane '$wanted{$ARGV} = \@F if $F[1] >= $wanted->{$ARGV}[1] && $F[0] =~ /22[78]/; } END { print "$_ : @$wanted{$_}" for keys %wanted;' *.csv
于 2010-10-16T10:04:38.157 回答
-1

看来您可以使用 $ARGV。

于 2010-10-16T09:59:28.520 回答