поменять grep с infile - PullRequest
       7

поменять grep с infile

1 голос
/ 13 января 2012

Я знаю, что об этом спрашивали много раз ... но я не могу понять, как выполнить эту простую задачу. Данные не отсортированы.

Пример данных:

file_1

E-J1-N4  
D-J5-N7  
F-J1-N5  
E-J5-N8  

file_2

E-J5-N8  
F-J5-N2  
E-J1-N4  
D-J5-N7    
F-J1-N5  
F-J5-N1  
F-J5-N12  
F-J5-N3 

(Я отредактировал данные, чтобы лучше отразить мой фактический набор данных, что, кажется, вызывает проблемы, это Nxx, N12 здесь. Как они правильно знают, данные не легко сортируются, я знаю, что я мог бы отформатировать все свои числа, чтобы N01 N02 и т. Д. Но если бы я мог избежать этого, было бы неплохо.)

Так что мне просто нужно напечатать $ имена в file_2, которых нет в file_1

grep -vf file_1 file_2  

не работает.

for name in `file_1`; do grep -v $name file_2; done  

дает мне тонну вывода ... (64 # имени с дубликатами). Цикл без -v flag тоже не работает, он добавляет данные. (wc -l не совпадает)

Так почему же grep -vf не работает? Может ли это быть проблема сортировки? Почему цикл не работает и, если это так, как я могу изменить grep в for loop?

Как всегда, большое спасибо за поиск! Я открыт и для других решений (awk, python).

Ответы [ 4 ]

1 голос
/ 13 января 2012
awk 'FNR==NR{a[$0];next}!($0 in a)' file_1 file_2
1 голос
/ 13 января 2012

Это будет работать:

comm -1 -3 <(sort file_1) <(sort file_2)

Тест:

[jaypal:~/Temp] comm -1 -3 <(sort file_1) <(sort file_2)
F-J5-N2
F-J5-N3
F-J6-N1
F-J6-N2
F-J6-N3
F-J6-N4
F-J6-N5
F-J6-N6
F-J6-N7
F-J6-N8
F-J8-N1
F-J9-N1
F-J9-N2

Обновление:

[jaypal:~/Temp] cat ff1
E-J1-N4
D-J5-N7
F-J1-N5
E-J5-N8

[jaypal:~/Temp] cat ff2
E-J5-N8
F-J5-N2
E-J1-N4
D-J5-N7
F-J1-N5
F-J5-N1
F-J5-N12
F-J5-N3

[jaypal:~/Temp] comm -1 -3 <(sort ff1) <(sort ff2)
F-J5-N1
F-J5-N12
F-J5-N2
F-J5-N3
1 голос
/ 13 января 2012

Это решение работает, только если в file_2 нет повторяющихся строк, а file_1 является подмножеством file_2:

sort file_[12] | uniq -u

Объясните: команда sort объединяет два файла, а затем сортирует их. Команда uniq затем выбирает только те строки, которые не дублируются, то есть те, которые находятся в file_2, но не в file_1.

Обратите внимание, что если вы замените флаг -u на -d , то результат будет состоять из дублированных строк, то есть значение появится в обоих файлах.

1 голос
/ 13 января 2012

В одну сторону, используя awk:

awk 'NR==FNR { a[$0]; next } !($0 in a)' file_1 file_2

Результат:

F-J5-N2
F-J5-N3
F-J6-N1
F-J6-N2
F-J6-N3
F-J6-N4
F-J6-N5
F-J6-N6
F-J6-N7
F-J6-N8
F-J8-N1
F-J9-N1
F-J9-N2
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...