Come unire file di testo?


21

Ho salvato molti documenti come txt. Voglio stamparli insieme, quindi prima li voglio insieme in un unico file. L'ordine non ha importanza in questo caso.

Voglio una soluzione che non implichi la digitazione dei nomi dei file da unire, ma una che unirebbe semplicemente tutti i file txt all'interno della cartella.

Posso farlo con un comando o qualche interfaccia grafica?


Ho guardato qui . Non so come usare join.

Risposte:


43

Utilizzare catcon il reindirizzamento dell'output. Sintassi: cat file [file] [[file] ...] > joined-file.

Esempio con solo due file (puoi averne molti altri):

$ echo "some text in a file" > file1
$ echo "another file with some text" > file2
$ cat file1 file2 > mergedfiles
$ cat mergedfiles
some text in a file
another file with some text

Nel caso in cui si disponga di "molti documenti", utilizzare la shell globbing (modelli):

cat input-files-dir/* > joined-file

Ciò unirà tutti i file in quella directory alla directory corrente (impedendo che corrisponda al file di output stesso). È totalmente indipendente dall'uso cate dal reindirizzamento dell'output: è solo Bash a fornire tutti i file come argomenti cat.


Tipi di file

Incollerà (unirà) i file insieme come faresti con carta e nastro. Non importa che il formato file effettivo sia in grado di gestirlo. Funzionerà per file di testo, ma non per PDF, ODT, ecc. Bene, li incollerà insieme, ma non è più un PDF / ODT valido.


Ordine di adesione

Come sottolineato da phoibos, il gorgogliamento della shell comporterà l'ordine alfabetico dei nomi dei file. Ecco come funziona il globbing di Bash e shell.


Addendum input file is output filesull'errore

Quando lo schema dei file di input corrisponde allo stesso file dell'output, ciò causerà un errore. È una funzione di sicurezza. Esempio: cat *.txt > out.txteseguire la seconda volta causerà questo.

Cosa puoi fare al riguardo:

  • Scegli un modello più specifico per abbinare i file di input effettivi, non corrispondendo al nome di output. Esempio: il modello di file di input *.txtcon il file di output output.outnon si scontrerà.
  • Lavora in diverse directory. Nell'esempio sopra ho usato una input-files-dirdirectory separata per posizionare tutti i file e l'output nella directory di lavoro corrente. Questo rende impossibile ottenere questo errore.

@cipricus Sì, ma questo è un gobbo di base molto semplice (modelli). Prova i tuoi schemi usando lssolo per elencare le partite. Ad esempio ls *.txtper vedere cosa viene abbinato.
gertvdijk,

2
@cipricus Che ne dici di cat * .txt> JoinedFile.txt?
Sadi,

1
Questo è il senso più comune in realtà, il gatto prima cattura tutti i file .txt e poi li unisce e in terzo luogo crea un nuovo file .txt che non può essere catturato al primo passo ;-)
Sadi

1
@cipricus Unisce solo i file. Come faresti usando pezzi di carta con colla e nastro adesivo! La maggior parte dei formati di file "documenti" come PDF, che sono compressi, non lo consentono. Usa un editor PDF. Comunque, la tua domanda riguardava i file di testo .
gertvdijk,

1
Comprendo appieno che il metodo che suggerisci (creare un sottodir, spostare i file e quindi unirti) potrebbe essere un modo migliore in alcuni casi. Ma se vogliamo solo unire tutti i file di testo (tutti con estensione .txt) nella directory corrente cat * .txt> JoinedFile.txt fa perfettamente il lavoro. L'ho appena provato per curiosità e funziona, e sembra che anche Cipricus abbia trovato lo stesso risultato. (E il sistema ha iniziato a lamentarsi del fatto che non dovremmo chattare qui, altrimenti ti chiederei se puoi insegnare a questo novizio come puoi usare la formattazione in questi commenti senza una barra degli strumenti ;-)
Sadi

12

Un modo semplice per farlo è usando cat:

cat file1 file2 > joined_file

Se emetti solo cat file1 file2vedrai entrambi i file nell'output standard. Usando >, stai semplicemente reindirizzando l'output standard su un file. Funzionerà anche con altri comandi.


Si prega di leggere la domanda. Stai dicendo di specificare i nomi dei singoli file, cosa che l'OP in particolare non voleva fare!
Sri

2
Questo è stato , non nella domanda originale. Non ho aggiornato la mia risposta da quando sono comparse risposte più complete.
Jorge Suárez de Lis,

@ JorgeSuárezdeLis Sebbene questa risposta non aiuti direttamente OP con la sua domanda, tieni presente che questa risposta probabilmente aiuterà qualcuno che ha solo alcuni file che vorrebbe unire. (oh hey, come me! grazie! ^ - ^) +1
Souta

@ JorgeSuárezdeLis In effetti. Hai risposto perfettamente alla revisione 2 della domanda. Pochi minuti dopo, la revisione 3 , ha modificato i requisiti relativi alle risposte.
gertvdijk,

5

Fallo con un semplice ciclo:

for i in *.txt; do cat "$i" >> complete.txt; done

>> accoda al file.

Nota: se per qualche motivo è necessario eseguire nuovamente il comando, è necessario rimuovere complete.txt, altrimenti si scriverà il file su se stesso, che non funziona.


5
Funzionerà anche questo, ma non vedo la necessità di un for-loop se puoi usare argomenti per cat.
gertvdijk,

1
Sì, hai ragione ovviamente. Non sono sicuro dell'ordinamento di Sord cat *.txt. Il ciclo for dovrebbe essere ordinato.
phoibos,


Sì, è esattamente lo stesso gorgoglio delle conchiglie. Non importa se lo usi in forqualsiasi altro posto in Bash.
gertvdijk,

4

Se i file che vuoi combinare finiscono tutti .txt, mantienili semplici:

cat *.txt > combined.txt

Se la directory contiene solo file di testo, è anche semplice:

cat * > combined.txt

(Nota che una volta creato combined.txt, farlo di nuovo lo includerebbe nell'espansione di* , portando a comportamenti strani).

Se vuoi selezionare alcuni file nella directory e non altri, è meglio se i nomi dei file ti permettono di distinguere quelli che desideri. Altrimenti, puoi divertirti con find. Ma dubito che tu debba andare così lontano.


thnx. se guardi i commenti alla risposta accettata, Sadi ha suggerito esattamente questo in un commento. se la tua risposta fosse stata la prima, sarebbe stato quello di cui avevo bisogno. dai un'occhiata anche al mio: aggiunto quello nel menu personalizzato

Grazie per il feedback. Sì, lo vedo ora, era un po 'oscurato ...
alexis,

4

Anche la sceneggiatura dell'azione personalizzata Thunar scritta da Cipricus mi ha ispirato a scrivere una sceneggiatura simile di Nautilus e ho pensato che potesse essere utile per gli altri che guardano queste domande e risposte come riferimento su questo argomento. Quindi eccolo qui:

#!/bin/sh
#Nautilus Script to join selected text files in a single file and open the joined file with default text editor
#
IFS=$'\n'
FILENAME="JoinedFile_$(date +%Y-%m-%d-%H-%M-%S).txt"
cat "$@" > "$FILENAME"
xdg-open "$FILENAME"

@David Foerster Grazie per la modifica. Non ho avuto problemi con la vecchia versione (con i miei casi di test limitati) e non vedo alcun problema con questa versione migliorata. Scusate se ho causato qualche inconveniente a causa di un difetto nella versione precedente.
Sadi,

Non era imperfetto, ma conteneva un ciclo non necessario, che rendeva il codice più difficile da capire, imho.
David Foerster,

2

Questo è un complemento e una variazione rispetto alle altre risposte, legate alla messa in opera di queste soluzioni nelle azioni dell'usanza di Thunar.

Non tutti sono utilizzabili in questo modo, ma alcuni lo sono.

Ho pensato che sarebbe stato molto interessante poter unire i file selezionati dal menu contestuale di Thunar .

Si tratta di una variazione da ciò che è stato suggerito da Sadi in un commento al gertvdijk 's risposta :

   cat %N > JoinedFile

Verranno uniti solo i file selezionati. Limitare le condizioni di aspetto ai file di testo.

inserisci qui la descrizione dell'immagine

inserisci qui la descrizione dell'immagine


Un ringraziamento speciale a Sadi, il cui commento mi ha fornito la soluzione più chiara e precisa al mio problema.

Ho accettato la risposta di gertvdijk come definitiva. Non solo è stata l'occasione per il commento di Sadi, ma sembra essere di ulteriore valore per gli altri, fornendo una soluzione ben argomentata e completa (anche se un po 'al di sopra delle mie capacità di lettura della CLI).


2

Potresti provare findanche il comando,

find . -name "*.txt" -type f -exec cat {} + > file

Trova i .txtfile all'interno della directory corrente ed esegue il catcomando su ogni file trovato . Alla fine l'intero output è stato reindirizzato al nome file file(creato direttamente all'interno della corrente stessa).

Spiegazione:

.                  # current directory

-name              # helps to find only .txt files.

-type f            # Only files

-exec cat {} +     # helps to run cat command on the founded .txt files.

>                  # Output redirection operator

file               # to store final output.

Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.