2017-01-23 18 views
1

私は2つのcsv(300,000行のA、1 000,000行のB)を持っています。レコードは列ID(関係1-1)によって関連付けられますが、列の順序は同じではなく、ID順ではありません。私は効率的に2つのcsvと+300000のレコードを比較する(awkで)

B.Field01,B.ID,B.Field02 
g,2,f 
f,4,r 
h,6,k 
a,1,3 

(私は時間を選択する、6

B.csv
A.ID,A.Field01,A.Field02 
2,a,d      
4,b,e      
1,c,f   

A.csv

AにIDが存在しないため、Bの700の000行を取得する必要が、k)

私はsqliteのようなsgbdで解決できると思いますが、awkのようにもっとシンプルで効率的な方法で解決できると確信しています。

私は私が見つけたこのコマンドを適応したい:

awk 'ARGIND==1 {x[$0]++; next} !x[$0]' B.csv A.csv 

は、しかし、これは全体のラインを比較して、私は比較するためのフィールドとして、具体的A.IDとB.IDを選択する方法がわかりません。

私はこれを解決する他の効率的なアプローチにも興味があります!

乾杯

答えて

5
$ awk -F"," 'FNR==NR{a[$1];next}!($2 in a)' a b 
B.Field01,B.ID,B.Field02 
h,6,k 
+0

ありがとうございました!それはまさに私が探していたものです。私はまた、他の貢献とコメントにも感謝しています。ではごきげんよう。 – Megamini

3

更新:

私はこれがJames Brown's awk solutionより良好に動作することを期待しているだろうが、私のテストはそれを証明することができませんでした。

2つのファイルでテストしましたが、両方とも700.000行あります。 awkのソリューションは大幅に高速でした。

awkソリューションには、B.csvのidカラムと同じくらいのメモリが必要です。そのため、本当に(実際には)大きなB.csvの場合、結合ソリューションが唯一の実現可能なソリューションかもしれません。 A.csvとB.csvが既にソートされている場合は、ほとんどの場合、sortコマンドが時間がかかるので、これははるかに優れています。


これは、両方の入力ファイルをソートするために必要な場合であっても、私はjoinコマンドは、このケースではかなりよく実行されます推測:

join -v2 -t, -11 -22 <(sed 1d A.csv|sort -t, -k1,1) <(sed 1d B.csv|sort -t, -k2,2) 

説明:

join 
---- 

-v2 only report lines with id unique to file2 
-t, input/output field separator 
-11 use field 1 from field 1 as id 
-22 use field 2 from field 2 as id 

sed 
--- 

1d removes the headers 


sort 
---- 

-t, delimiter 
-k1,1 sort based on field 
+1

結合ソリューションはawkよりも効率的でなければなりません。 OPは300k行だと言ったので、大きなファイルです。 +1 – NinjaGaiden

+1

私はしばしば、 "派手な"オプションでhead/tailを使うのが好きです。ここで: 'sed 1d file' –

+0

@glennjackman移植可能なシェルスクリプト' sed'が良い選択であると私は同意します。 – hek2mgl

関連する問題