Сравнение двух текстовых файлов

У меня есть 2 больших файла CSV, file1.csv, который выглядит так

1,2,3,4
1,4,5,6
1,7,8,9
1,11,13,17

file2.csv, который выглядит так

1,2,3,4
1,7,8,9
2,4,9,10
13,14,17,18

Это просто случайные числа, которые я составил, в основном два числа, которые идентичны и отсортированы. Я хочу сравнить file1.csv и file2.csv, а затем скопировать строки, которые присутствуют в file1.csv, но не в file2.csv, в file3.csv. разделитель, очевидно, запятая

Я старался

comm -2 -3 file.csv file2.csv > file3.csv

и я попробовал

diff -u file.csv file2.csv >> file3.csv

Оба не работали, потому что file3 был больше, чем file1 и file2. Я пробовал разные diff а также comm Команды, иногда они больше, чем file2 и примерно того же размера, что и file file1, я знаю, что file3 должен быть значительно меньше по размеру, чем file1 и file2. И конечно я посмотрел на file3, а не на те результаты, которые хотел

На данный момент я знаю, что это можно сделать с diff или же comm но я не знаю команду для использования.

4 ответа

Решение

Попробуйте эту команду:

 grep -v -f file2.csv file1.csv > file3.csv

Согласно инструкции grep:

  -f FILE, --file=FILE
          Obtain  patterns  from  FILE,  one  per  line.   The  empty file
          contains zero patterns, and therefore matches nothing.   (-f  is
          specified by POSIX.)

  -v, --invert-match
          Invert the sense of matching, to select non-matching lines.  (-v
          is specified by POSIX.)

Как сказал Steeldriver в своем комментарии, лучше добавить также -x а также -F тот:

  -F, --fixed-strings
          Interpret PATTERN as a  list  of  fixed  strings,  separated  by
          newlines,  any  of  which is to be matched.  (-F is specified by
          POSIX.)
  -x, --line-regexp
          Select  only  those  matches  that exactly match the whole line.
          (-x is specified by POSIX.)

Итак, лучшая команда:

 grep -xvFf file2.csv file1.csv > file3.csv

Эту команду используют file2.csv линия как шаблон и печать линии file1.csv это не соответствует (-v).

Для того, чтобы иметь возможность использовать comm, вы должны сначала отсортировать строки.

comm -23 <(sort file1.csv) <(sort file2.csv) > file3.csv

С помощью diff команда сделать grep и не требуется хранение.

Выведите, если строки существуют в файле1, но отсутствуют в файле2:

$ diff file{1,2}.csv | grep -Po "^< \K.*"
1,4,5,6
1,11,13,17

И вывод, если строки существуют в file2, но не в file1, просто меняя левый угол (<) под прямым углом (>):

$ diff file{1,2}.csv | grep -Po "^> \K.*"
2,4,9,10
13,14,17,18

Опция Python:

#!/usr/bin/env python3

import sys

def readfile(file):
    with open(file) as src:
        return [line.strip() for line in src.readlines()]

lines_1 = readfile(sys.argv[1]); lines_2 = readfile(sys.argv[2])

for line in lines_1:
    if not line in lines_2:
        print(line)

Выход:

1,4,5,6
1,11,13,17

Вставьте скрипт в пустой файл как extract.py, сделайте его исполняемым и запустите его командой:

<script> <file_1> <file_2>

Или, чтобы написать это непосредственно в file_3:

<script> <file_1> <file_2> >file_3
Другие вопросы по тегам