0

同じ形式の複数のファイルをマージして、特定の列の値を追加し、他の列を修正するにはどうすればよいですか?

ファイルの列が次の形式の場合 (複数の行がある場合):

File 1:
a1 b1 c1 d1 e1

File 2:
a2 b2 c2 d2 e2

File n:
an bn cn dn en

where a1=a2=an, b1=b2=bn

Output:
a b (c1+c2+...cn) (d1+d2+...dn) (e1+e2+...en)

For example,

File 1:
1 0 200 5 50
2 1 345 9 22
3 2 287 4 33

File 2:
1 0 355 4 12
2 1 366 5 7
3 2 202 7 16

I want the Output:
1 0 555 9 62
2 1 711 14 29
3 2 489 11 49
4

3 に答える 3

1

awk-oneliner:

awk '{i=$1" "$2;a[i]+=$3;b[i]+=$4;c[i]+=$5}END{for(x in a)print x,a[x],b[x],c[x]}' file*

3 つのファイルでテストします (oneliner は n 個のファイルで動作します)

kent$  head file*
==> file1 <==
1 0 200 5 50
2 1 345 9 22
3 2 287 4 33

==> file2 <==
1 0 355 4 12
2 1 366 5 7
3 2 202 7 16

==> file3 <==
1 0 30 41 120
2 1 306 15 70
3 2 230 7 20

kent$  awk '{i=$1" "$2;a[i]+=$3;b[i]+=$4;c[i]+=$5}END{for(x in a)print x, a[x],b[x],c[x]}' file*
1 0 585 50 182
2 1 1017 29 99
3 2 719 18 69
于 2012-10-12T14:39:09.170 に答える
0

達人が与えたものの同様の解決策ですが、 n個のファイルに対して一般化されています:

次の入力ファイルを想定しています。

==> file1 <==
1 0 200 5 50
2 1 345 9 22
3 2 287 4 33

==> file2 <==
1 0 355 4 12
2 1 366 5 7
3 2 202 7 16

==> file3 <==
1 0 400 6 14
2 1 500 5 7
3 2 202 7 16

このawkスクリプトを実行します。

awk '
    FNR < NR { 
        exit; 
    } 
    {
        for ( i = ARGC - 1; ARGV[i] != FILENAME; i-- ) {
            getline line < ARGV[i];
            r = split( line, fields );
            if ( r < 3 ) {
                continue;
            }
            if ( $1 == fields[1] && $2 == fields[2] ) {
                for ( j = 3; j <= NF; j++ ) {
                    $j += fields[j];
                }
            }
        }
        print;
    }
' file[123]

その結果、次のようになります。

1 0 955 15 76
2 1 1211 19 36
3 2 691 18 65
于 2012-10-12T14:32:00.033 に答える
0
$ awk '{getline x <f; split(x,a," ");$3+=a[3];$4+=a[4];$5+=a[5]}1' f="file1" file2
1 0 555 9 62
2 1 711 14 29
3 2 489 11 49

getline を使用すると、他の行の内容も並行して読み取ることができます。2 番目のファイルの内容も分割すると、合計できます。

于 2012-10-12T14:14:16.713 に答える