Unisci righe alternative da due file


9

file1:

.tid.setnr := 1123 
.tid.setnr := 3345 
.tid.setnr := 5431
.tid.setnr := 89323

file2:

.tid.info := 12
.tid.info := 3
.tid.info := 44
.tid.info := 60

File di uscita:

.tid.info := 12
.tid.setnr := 1123
.tid.info := 3
.tid.setnr := 3345
.tid.info := 44
.tid.setnr := 5431
.tid.info := 60
.tid.setnr := 89323

2
Si prega di menzionare sempre il proprio sistema operativo. Molti strumenti standard si comportano in modo diverso sui diversi sistemi operativi, quindi dobbiamo sapere cosa stai usando.
terdon

Risposte:




5

La pastesoluzione è la più portatile ed efficiente. Sto solo citando questa alternativa nel caso in cui preferisci il suo comportamento nel caso in cui i due file non abbiano lo stesso numero di righe:

Con GNU sed:

sed Rfile1 file2

Se file1ha meno righe di file2, allora quando file1è esaurito, sednon produrrà nulla per esso (al contrario di linee vuote per paste).

Se file1ha più righe di file2, allora quelle righe extra verranno scartate (invece di stampare righe vuote per file2con paste).

$ paste a b
1       a
2       b
3
4
$ paste -d \\n a b
1
a
2
b
3

4

$ sed Rb a
1
a
2
b
3
4
$ sed Ra b
a
1
b
2

4

Utilizzando awk( gawk, nawk, mawk):

awk 'NR==FNR {x[FNR]=$0;next} {print x[FNR]"\n"$0}' file2 file1 > outputfile
  • NR==FNR {x[FNR]=$0;next}: NR==FNRviene confrontato solo se il numero del record corrente è uguale al numero del record del file corrente (quindi viene confrontato solo durante l'elaborazione del primo file): memorizza il record attualmente elaborato nella matrice xin un indice uguale al numero del record del file corrente e salta il record corrente
  • {print x[FNR]"\n"$0}: stampa il contenuto dell'array xsu un indice uguale al numero del record del file corrente seguito da una nuova riga e dal contenuto del record corrente
~/tmp$ cat file1
.tid.setnr := 1123
.tid.setnr := 3345
.tid.setnr := 5431
.tid.setnr := 89323
~/tmp$ cat file2
.tid.info := 12
.tid.info := 3
.tid.info := 44
.tid.info := 60
~/tmp$ awk 'NR==FNR {x[FNR]=$0;next} {print x[FNR]"\n"$0}' file2 file1
.tid.info := 12
.tid.setnr := 1123
.tid.info := 3
.tid.setnr := 3345
.tid.info := 44
.tid.setnr := 5431
.tid.info := 60
.tid.setnr := 89323

Sta dando l'output ma non è esattamente quello che volevo. Le righe tid.info stanno arrivando dopo le righe tid.setnr nel mio file di output.
pmaipmui,

@Nainita Questo è quello che stai mostrando nel tuo esempio di output.
kos

@Nainita Ad ogni modo per cambiare l'ordine dell'output puoi semplicemente cambiare file1e file2nel comando.
kos,

Sì ... ho fatto lo stesso ma stava stampando esattamente come prima. dopo aver stampato tid.setnr, è stato stimolante tid.info.
pmaipmui,

1
@mikeserv Comunque da quando ci sono stato ho provato mawkanche, e funziona anche su di esso. Comunque sia ragionevole non riesco a capire perché non dovrebbe funzionare esattamente al contrario (cioè semplicemente cambiando file). Non è che si awkpreoccupi dell'input, le linee sono linee. Se qualcosa non fosse supportato dalla sua versione, si sarebbe appena rotto la prima volta. Molto più facilmente, semplicemente OP ha fatto un errore a cambiare i file di input negli argomenti.
kos

-1

Di seguito la soluzione più semplice.

cat file1 >> file2

o

cat file2 >> file1

1
sachin, leggi di nuovo la domanda; questo accoda il contenuto di un file al contenuto di un altro file. Non unisce i file alternando le righe (quindi una riga da file1allora una riga da file2e così via ...)
don_crissti
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.