古い、bashの回答(O(n);2 * n
ファイルを開く)
@ mjgpy3の回答から、次のようにforループを作成して使用する必要がありますcomm
。
#!/bin/bash
tmp1="/tmp/tmp1$RANDOM"
tmp2="/tmp/tmp2$RANDOM"
cp "$1" "$tmp1"
shift
for file in "$@"
do
comm -1 -2 "$tmp1" "$file" > "$tmp2"
mv "$tmp2" "$tmp1"
done
cat "$tmp1"
rm "$tmp1"
に保存し、comm.sh
実行可能にして、
./comm.sh *.sp
すべてのファイル名が。で終わると仮定します.sp
。
更新された回答、pythonは、各ファイルを1回だけ開きます
他の答えを見て、一時ファイルを使用せずにファイルごとに1回開き、重複行をサポートするものを提供したいと思いました。さらに、ファイルを並行して処理しましょう。
ここに行きます(python3で):
#!/bin/env python
import argparse
import sys
import multiprocessing
import os
EOLS = {'native': os.linesep.encode('ascii'), 'unix': b'\n', 'windows': b'\r\n'}
def extract_set(filename):
with open(filename, 'rb') as f:
return set(line.rstrip(b'\r\n') for line in f)
def find_common_lines(filenames):
pool = multiprocessing.Pool()
line_sets = pool.map(extract_set, filenames)
return set.intersection(*line_sets)
if __name__ == '__main__':
# usage info and argument parsing
parser = argparse.ArgumentParser()
parser.add_argument("in_files", nargs='+',
help="find common lines in these files")
parser.add_argument('--out', type=argparse.FileType('wb'),
help="the output file (default stdout)")
parser.add_argument('--eol-style', choices=EOLS.keys(), default='native',
help="(default: native)")
args = parser.parse_args()
# actual stuff
common_lines = find_common_lines(args.in_files)
# write results to output
to_print = EOLS[args.eol_style].join(common_lines)
if args.out is None:
# find out stdout's encoding, utf-8 if absent
encoding = sys.stdout.encoding or 'utf-8'
sys.stdout.write(to_print.decode(encoding))
else:
args.out.write(to_print)
に保存してfind_common_lines.py
、
python ./find_common_lines.py *.sp
--help
オプションでより多くの使用法情報。