Jak usunąć słowa z pliku txt, który istnieje w innym pliku txt?

8

Plik a.txtma około 100 000 słów, każde słowo znajduje się w nowej linii

july.cpp
windows.exe
ttm.rar
document.zip

Plik b.txtzawiera 150 000 słów, jedno słowo po wierszu - niektóre słowa pochodzą z pliku a.txt, ale niektóre są nowe:

july.cpp    
NOVEMBER.txt    
windows.exe    
ttm.rar    
document.zip    
diary.txt

Jak mogę scalić te pliki w jeden, usunąć wszystkie zduplikowane linie i zachować nowe linie (linie, które istnieją, a.txtale nie istnieją b.txti odwrotnie)?

Kate-Kasia
źródło
Czy chętnie użyjesz Pythona?
Tim
2
@ MikołajBartnicki Unix.SE prawdopodobnie byłby lepszym miejscem do zapytania
Glutanimate
1
Kasiu, popełniłem błąd w odpowiedzi, dlatego ją usunąłem. Pracuję nad nowym.
2
@Glutanimate To pytanie jest tutaj w porządku.
Seth
1
@ Glutanimate Ach, przepraszam, jakoś przegapiłem ten komentarz.
Seth

Odpowiedzi:

13

Jest to polecenie, aby to zrobić: comm. Jak stwierdzono w man comm, jest to po prostu proste:

   comm -3 file1 file2
          Print lines in file1 not in file2, and vice versa.

Pamiętaj, że commoczekuje ona sortowania zawartości plików, dlatego musisz je posortować przed ich wywołaniem comm:

sort unsorted-file.txt > sorted-file.txt

Więc by podsumować:

sort a.txt > as.txt

sort b.txt > bs.txt

comm -3 as.txt bs.txt > result.txt

Po powyższych poleceniach będziesz mieć oczekiwane linie w result.txtpliku.


źródło
dziękuję, działa jak urok. PS. do zdjęcia z tłuczkiem na Twoim profilu jest fajne ;-)
Kate-Kasia
2

Oto krótki skrypt python3, oparty na odpowiedzi Germara , który powinien to zrobić, zachowując b.txtnieposortowaną kolejność.

#!/usr/bin/python3

with open('a.txt', 'r') as afile:
    a = set(line.rstrip('\n') for line in afile)

with open('b.txt', 'r') as bfile:
    for line in bfile:
        line = line.rstrip('\n')
        if line not in a:
            print(line)
            # Uncomment the following if you also want to remove duplicates:
            # a.add(line)
Lily Chung
źródło
1
#!/usr/bin/env python3

with open('a.txt', 'r') as f:
    a_txt = f.read()
a = a_txt.split('\n')
del(a_txt)

with open('b.txt', 'r') as f:
    while True:
        b = f.readline().strip('\n ')
        if not len(b):
            break
        if not b in a:
            print(b)
Germar
źródło
2
Człowieku, strzelasz do komara z armaty morskiej!
:-) Masz rację. Brakowało mi „k” na 100 tys.
Germar
1

Spójrz na commkomendę coreutils -man comm

NAME
       comm - compare two sorted files line by line

SYNOPSIS
       comm [OPTION]... FILE1 FILE2

DESCRIPTION
       Compare sorted files FILE1 and FILE2 line by line.

       With  no  options,  produce  three-column  output.  Column one contains
       lines unique to FILE1, column two contains lines unique to  FILE2,  and
       column three contains lines common to both files.

       -1     suppress column 1 (lines unique to FILE1)

       -2     suppress column 2 (lines unique to FILE2)

       -3     suppress column 3 (lines that appear in both files)

Na przykład możesz to zrobić

$ comm -13 <(sort a.txt) <(sort b.txt)
diary.txt
NOVEMBER.txt

(linie unikalne dla b.txt)

steeldriver
źródło