2011-08-18 24 views
1

我想在bash中排序一些數據。數據如下所示。排序一些數據

20110724.gz 1347 
    20110724.gz 2128 
    20110725.gz 1315 
    20110725.gz 2334 
    20110726.gz 808 
    20110726.gz 1088 
    -bash-3.2$ 

排序後,它應該看起來像

20110724.gz 3475 
    20110725.gz 3649 
    20110726.gz 1896 

基本上,對於給定的日期,數據相加。有人可以幫忙嗎?謝謝。

嗯,希望我能在幾天內搞清楚。

回答

0

你不需要perl來做這件事。一些外殼欺騙將幫助:)

sort -n -k1,8 <file | while true ; do 
    if ! read line ; then 
     test -n "$accfile" && echo $accfile $value 
     break 
    fi 
    line=$(echo $line | tr -s ' ') 
    curfile=$(echo $line | cut -d\ -f1) 
    curvalue=$(echo $line | cut -d\ -f2) 
    if [ $curfile != "$accfile" ] ; then 
     # new file, output the last if not empty 
     test -n "$accfile" && echo $accfile $value 
     accfile=$curfile 
     value=$curvalue 
    else 
     value=$(expr $value \+ $curvalue) 
    fi 
done 

k參數告訴排序什麼字符用於排序。由於日期以數字排序的格式顯示,因此可以使用數字排序(-n)。

+0

你錯過了總結部分。我不認爲排序是足夠的。 –

+0

哎呀,我錯過了總結部分!你是對的!我們來看看... –

+0

已更新。單獨使用shell並不容易,但我想花一些時間記住我編寫腳本的黃金時間:) –

0

這是一個perl解決方案。

用法:script.pl input.txt > output.txt

代碼:

use warnings; 
use strict; 
use ARGV::readonly; 

my %sums; 
while (<>) { 
    my ($date, $num) = split; 
    $sums{$date} += $num; 
} 
for my $date (sort keys %sums) { 
    print "$date $sums{$date}\n"; 
} 

或者作爲一個班輪:

$ perl -we 'my %h; while(<>) { ($d,$n)=split; $h{$d}+=$n; } print "$_ $h{$_}\n" for sort keys %h;' data2.txt 

如果你確實需要在日期的數字排序:

sort { substr($a,0,8) <=> substr($b,0,8) } keys %sums; 
1

這裏有一個快速和骯髒的Perl oneliner:

$ perl -e 'my %h =(); while (<>) { chomp; my ($fname, $count) = split; $h{$fname} += $count;} foreach my $k (sort keys %h) {print $k, " ", $h{$k}, "\n"}' < datafile