2017-02-04 6 views
0

Ich habe eine Textdatei Namen coalitions.txt und es sieht wie folgt aus:Warum funktioniert diese sed nicht?

Hadash left 
Balad left 
Raam_Taal left 
Meretz left 
Shas right 
Habait_Hayehudi right 
Haihud_Haleumi right 
Yehadut_Hatorah right 
Liberman right 
Avoda left 
Kadima center 
Likud right 

Ich möchte eine Liste der letzten Worte in jeder Zeile ohne Duplikate, drucken. Die Ausgabe sollte sein:

left 
right 
center 

Ich weiß, dass ich viele Techniken wie tail verwenden, aber ich möchte wissen, warum das, was ich getan habe funktioniert nicht ... Ich habe versucht, dieses:

cat coalitions.txt | sed 's/.*[[:space:]]\+\([A-Z][a-z]\+\)/\1/' | sort | uniq 

es aber druckt nur die selbe Liste erneut, als ob meine sed nicht funktioniert. Warum passiert dies?

+0

Wenn Sie sich fragen, finden „* Warum ist das nicht funktioniert sed *?“ - ** Hinweis: ** Es ist wahrscheinlich nicht 'Schuld sed'. –

+0

Sollte die Ausgabe nicht "Mitte links rechts" (sortiert) sein? –

Antwort

0

Das hier

[A-Z][a-z]\+ 

ist "eine von A-Z, gefolgt von einem oder mehreren von a-z". Was Sie gemeint ist wahrscheinlich [A-Za-z], oder noch besser und nicht anfällig für locale Variationen, [[:alpha:]].

würde ich extrahieren nur das letzte Wort jeder Zeile wie folgt aus:

sed 's/.*[[:space:]]\([^[:space:]]*\)$/\1/' coalitions.txt | sort -u 

Keine Notwendigkeit für separate cat und sort | uniq ist die gleiche wie sort -u.

+0

Warum "[[: space:]] \ +" nicht funktioniert? – TopCaver

+0

@TopCaver Es würde funktionieren (zumindest in GNU sed), aber es wird nicht benötigt. –

0

das richtige Werkzeug für den Job verwenden:

$ awk '!z[$NF]++ {print $NF}' coalitions.txt 
left 
right 
center 
0

Ich denke, sed nicht erkennt + als Meta-Zeichen für 1 oder mehr. Du kannst es versuchen.

cat coalitions.txt | sed 's/.* \([A-Za-z][A-Za-z]*\)/\1/' | sort | uniq 
+0

'\ +' ist eine Erweiterung auf Basis Regular Expression von mindestens GNU anerkannt sed. –

+0

@ BenjaminW. Vielen Dank. Ich habe es auf einer Mac-Maschine versucht, es wird nicht erkannt, aber auf einer anderen Linux-Maschine ist es. – Shiping

+0

Ihre Lösung behebt das Problem trotzdem und ist POSIX-konform. –

0
cat coalitions.txt | sed 's/.*\s\+\([A-Za-z]\+\)/\1/' 

Dies scheint zu funktionieren. Da ich auf einem Windows-bin muss ich \s statt [[:space:]] verwenden. Aber selbst wenn ich nur den Platz ändere und versuche:

cat coalitions.txt | sed 's/.*\s\+\([A-Z][a-z]\+\)/\1/' 

Es funktioniert nicht. Das Problem besteht darin, dass der Zeichenbereich ein Komma und keine separate Klammer verwenden muss. [A-Za-z]

+0

Sie wollen wahrscheinlich nicht das Komma in '[A-Z, a-z]', wenn Sie tatsächlich ein Komma übereinstimmen sollen. –

+0

Warum funktioniert es dann? –

+0

Ich sage nicht, es nicht funktioniert, aber '[A-Z, a-z]' Spiele Buchstaben _and comma_, während es einfach "Buchstaben", wie in '[A-Za-z]' scheint gemeint. Kein Komma erforderlich. –