Dlaczego to nie działa? „Ls * .txt | xargs cat> all.txt ”(wszystkie pliki w jednym dokumencie txt)
20
Dlaczego to nie działa?
ls *.txt | xargs cat > all.txt
(Chcę połączyć zawartość wszystkich plików tekstowych w pojedynczy plik „all.txt”). Find z -exec powinien również działać, ale naprawdę chciałbym zrozumieć składnię xargs.
Chociaż nie używaj lsdo tego . Jeśli naprawdę nie możesz użyć, cat *.txt >all.txtspróbuj, printf '%s\0' *.txt | xargs -r0 cat >alla następnie mv all all.txtunikaj odwoływania się do pliku.
tripleee
Odpowiedzi:
27
ls *.txt | xargs cat >> all.txt
może działać nieco lepiej, ponieważ dołączałby do pliku all.txt zamiast tworzyć go ponownie po każdym pliku.
Cat * .txt> all.txt jest oczywiście lepszy. Dzięki
ajo
1
Jednak ... | xargs cat >> all.txt lub> all.txt zawsze zwracają błąd z xargs: niedopasowany pojedynczy cudzysłów ... Czy to dlatego, że xargs bierze wszystko za nim jako polecenie?
ajo
1
Czy masz nazwy plików ze spacjami? Jeśli tak, użyj zamiast tego czegoś w rodzaju „znajdź / twoja / ścieżka -nazwa” * .txt '-print0 | xargs -0 cat >> all.txt ”
Janne Pikkarainen
1
nie, zastąpiłem wszystkie spacje plików . Ale myśląc o tym, niektóre nazwy plików mogą zawierać pojedyncze cudzysłowy, ponieważ w listing_O'Connor .txt może to być problem!
ajo
Tak, to jest problem. :) Najłatwiejszym i najrozsądniejszym sposobem jest użycie find z -print0 w połączeniu z xargs -0 - wtedy cały łańcuch użyje znaku NULL jako separatora i białych znaków, a znaki specjalne będą obsługiwane automatycznie.
Janne Pikkarainen
3
Jeśli niektóre nazwy plików zawierają „,” lub spacja xargsnie powiedzie się z powodu problemu z separatorem
Zasadniczo nigdy nie biegnij xargsbez -0, ponieważ wróci i cię ugryzie.
Nadal występuje następujący błąd: xargs: niedopasowany pojedynczy cytat; domyślnie cytaty są specjalne dla xargs, chyba że użyjesz opcji -0
ajo
1
Czy masz plik .txt z pojedynczym cytatem w nazwie?
Jeremy Smyth,
0
Możesz także natknąć się na ograniczenie długości linii poleceń. Jednym z powodów użycia xargsjest to, że dzieli dane wejściowe na bezpieczne fragmenty wielkości wiersza polecenia. Wyobraź sobie więc sytuację, w której masz w katalogu setki tysięcy plików .txt. ls *.txtzawiedzie. Musisz to zrobić
ls | grep .txt$ |xargs cat > /some/other/path/all.txt
.txt$w tym przypadku jest wyrażenie regularne pasujące do wszystkiego, co kończy się na .txt (więc nie jest dokładnie tak *.txt, ponieważ jeśli masz plik o nazwie atxt, to *.txtnie pasuje do niego, ale wyrażenie regularne tak.)
Zastosowanie innej ścieżki polega na tym, że, jak wskazały inne odpowiedzi, plik all.txt jest dopasowywany do wzorca, *.txtco spowodowałoby konflikt między danymi wejściowymi i wyjściowymi.
Pamiętaj, że jeśli masz 'w nazwie jakieś pliki (i może to być przyczyną unmatched single quotebłędu), powinieneś to zrobić
Opcja --null mówi grepowi, aby używał danych wyjściowych oddzielonych znakiem \0(aka null) zamiast domyślnego znaku nowej linii, a -0opcja `xargs mówi, że oczekuje wejścia w tym samym formacie. Działa to nawet, jeśli masz nazwy plików z nowymi liniami.
ls
do tego . Jeśli naprawdę nie możesz użyć,cat *.txt >all.txt
spróbuj,printf '%s\0' *.txt | xargs -r0 cat >all
a następniemv all all.txt
unikaj odwoływania się do pliku.Odpowiedzi:
ls *.txt | xargs cat >> all.txt
może działać nieco lepiej, ponieważ dołączałby do pliku all.txt zamiast tworzyć go ponownie po każdym pliku.
Nawiasem mówiąc,
cat *.txt >all.txt
działałoby również. :-)źródło
Jeśli niektóre nazwy plików zawierają „,” lub spacja
xargs
nie powiedzie się z powodu problemu z separatoremZasadniczo nigdy nie biegnij
xargs
bez -0, ponieważ wróci i cię ugryzie.Zamiast tego rozważ użycie GNU Parallel:
lub jeśli wolisz:
Dowiedz się więcej o GNU Parallel http://www.youtube.com/watch?v=OpaiGYxkSuQ
źródło
all.txt
jest plikiem w tym samym katalogu, więc cat jest zdezorientowany, gdy chce pisać z tego samego pliku do tego samego pliku.Z drugiej strony:
Spowoduje to odczytanie plików tekstowych z bieżącego katalogu do pliku all.txt w podkatalogu (nie jest dołączony
*.txt
).źródło
Możesz także natknąć się na ograniczenie długości linii poleceń. Jednym z powodów użycia
xargs
jest to, że dzieli dane wejściowe na bezpieczne fragmenty wielkości wiersza polecenia. Wyobraź sobie więc sytuację, w której masz w katalogu setki tysięcy plików .txt.ls *.txt
zawiedzie. Musisz to zrobić.txt$
w tym przypadku jest wyrażenie regularne pasujące do wszystkiego, co kończy się na .txt (więc nie jest dokładnie tak*.txt
, ponieważ jeśli masz plik o nazwieatxt
, to*.txt
nie pasuje do niego, ale wyrażenie regularne tak.)Zastosowanie innej ścieżki polega na tym, że, jak wskazały inne odpowiedzi, plik all.txt jest dopasowywany do wzorca,
*.txt
co spowodowałoby konflikt między danymi wejściowymi i wyjściowymi.Pamiętaj, że jeśli masz
'
w nazwie jakieś pliki (i może to być przyczynąunmatched single quote
błędu), powinieneś to zrobićOpcja --null mówi grepowi, aby używał danych wyjściowych oddzielonych znakiem
\0
(aka null) zamiast domyślnego znaku nowej linii, a-0
opcja `xargs mówi, że oczekuje wejścia w tym samym formacie. Działa to nawet, jeśli masz nazwy plików z nowymi liniami.źródło