2017-10-02 1 views
0

J'ai 2 fichiers csv, ce sont leurs contenus.Comment fusionner deux fichiers avec la même valeur de colonne dans bash

fichier1 (23) champs

data11,data12,ID1,data14... 

data21,data22,ID2,data24... 

data31,data32,ID3,data34... 

file2 (22) champs

ID1,value12,value13,... 

ID1,value22,value23,... 

ID1,value32,value33,... 

ID2,value42,value43,... 

ID3,value52,value53,... 

La sortie doit être ...

SORTIE:

data11,data12,ID1,data14,...,value12,value13 

data11,data12,ID1,data14,...,value22,value23 

data11,data12,ID1,data14,...,value32,value33 

data21,data22,ID2,data24,...,value42,value43 

data31,data32,ID3,data34,...,value52,value53 

Quelqu'un peut-il m'aider à obtenir cette sortie en utilisant awk ou bash built-ins? Merci!

+0

est ce ', ...,' implique plusieurs colonnes intermédiaires? Quel est le nombre de champs dans chaque fichier? – RomanPerekhrest

+0

Oui, vous avez raison. Pour le fichier 1 il y a 23 champs et pour le fichier 2 il y a 22 champs –

+0

pouvez-vous poster le fragment d'entrée avec TOUS les champs? – RomanPerekhrest

Répondre

0

Vous pouvez utiliser join ..Specify l'ordre des colonnes r par exemple pour la sortie après -o par exemple: 1.1 se rapporte à la première colonne du 1er fichier (file1). Il est également nécessaire de pré-trier les fichiers d'entrée

join -t "," -1 3 -2 1 -o 1.1,1.2,1.3,1.4,2.2,2.3 
<(sort -t "," -k3 /tmp/file1) <(sort -t "," -k1 /tmp/file2) 
+0

Mais dans mon cas ID n'est pas un nombre entier. C'est une chaîne de caractères aléatoires. peut rejoindre encore le soutenir? –

+0

Oui, nous trions les deux entrées ici en fonction de la colonne qui n'est pas nécessairement un tri numérique. essayez d'utiliser ceci et faites le moi savoir. Quelques ajustements pourraient être exigés pour préparer les dossiers d'entrée. –

0

Désolé, ma faute à se méprendre ur problème, essayez ce qui suit cmd, il doit être ce que tu veux:

for line1 in `cat file1`;do id=`echo $line1|awk -F ',' '{print $3}'`;\ 
awk -v id=$id -v line1=$line1 -F ',' '($1==id){print line1","$0}' file2;done 

la sortie de ce cmd est

data11,data12,ID1,data14...,ID1,value12,value13,... 
data11,data12,ID1,data14...,ID1,value22,value23,... 
data11,data12,ID1,data14...,ID1,value32,value33,... 
data21,data22,ID2,data24...,ID2,value42,value43,... 
data31,data32,ID3,data34...,ID3,value52,value53,... 

et si u n » t veulent la colonne répétée d'ID *, u peut le faire comme

for line1 in `cat file1`;do id=`echo $line1|awk -F ',' '{print $3}'`;\ 
awk -v id=$id -v line1=$line1 -F ',' '($1==id){printf "%s",line1;\ 
for(i=2;i<NF;i++) printf ",%s",$i;print ","$NF}' file2;done 

il ne sera pas imprimer ID * dans fichier2

data11,data12,ID1,data14...,value12,value13,... 
data11,data12,ID1,data14...,value22,value23,... 
data11,data12,ID1,data14...,value32,value33,... 
data21,data22,ID2,data24...,value42,value43,... 
data31,data32,ID3,data34...,value52,value53,... 

---------- mauvaise réponse avant mise à jour ---------

https://www.computerhope.com/unix/upaste.htm HI,

u peut utiliser paste cmd pour rejoindre lignes connexes de fichiers différents

s'il vous plaît utiliser man paste cmd pour une utilisation détaillée

+0

Mais je pense que ce problème est plus compliqué. Je pense que je ne peux pas utiliser paste cmd ici, car il y a des vérifications de colonnes. –

+0

@JaneS. Donc désolé de mal comprendre votre problème, s'il vous plaît vérifier ma réponse mise à jour. –