2012-05-14 10 views
5

bekam ich eine Zeichenfolge, die wie folgt aussieht:Bash - Auszug Zahlen von String

„abcderwer 123.123 10.200 asdfasdf iopjjop“

Jetzt möchte ich die Nummern, die Regelung xx folgende, xxx wobei x ein Nummer zwischen 0-9. Z.B. 10.200. Muss fünfstellig sein und muss "," enthalten.

Wie kann ich das tun?

Danke

Antwort

9

Sie grep verwenden können:

$ echo "abcderwer 123123 10,200 asdfasdf iopjjop" | egrep -o '[0-9]{2},[0-9]{3}' 
10,200 
+0

große Antwort, danke – user1360250

1

Check out Pattern-Matching und reguläre Ausdrücke.

Links:

Bash regular expressions

Patterns and pattern matching

SO question

und wie oben erwähnt, besteht eine Möglichkeit Musteranpassung zu verwenden, ist mit grep. Andere Verwendungen: Echo unterstützt Muster (Globbing) und unterstützt reguläre Ausdrücke.

+1

'echo' nicht und' finden' ist nicht auf die Frage anwendbar. –

+0

@DennisWilliamson Ich habe nie gesagt, dass sie es waren. Und Sie können Muster mit Echo verwenden. Beispiel: echo * oku? Ent? würde "Dokumente" zurückgeben, wenn Sie sich in einem normalen Home-Ordner befinden. Ich weiß, dass du Regex gemeint hast, aber ich werde das bearbeiten :) – keyser

+0

Das ist keine Regex, das ist Globbing. –

0

Einfache Mustererkennung (Glob-Muster) ist in die Shell integriert. Vorausgesetzt, dass Sie die Saiten in $* haben (das heißt, sie sind Befehlszeilenargumente an das Skript, oder haben Sie set an einer Schnur verwendet man sonst erhalten haben), versuchen Sie dies:

for token; do 
    case $token in 
    [0-9][0-9],[0-9][0-9][0-9]) echo "$token" ;; 
    esac 
done 
+1

Das wäre '$ @'. Es besteht ein Unterschied. –

+0

Wenn Sie auf die Befehlszeile zugreifen, gibt es sicherlich einen Unterschied zwischen '$ *' und '$ @'; aber ich wählte ausdrücklich die Variable, die das Array 'argv' enthält, nach ihrem ursprünglichen Bourne-Namen, weil das der Name ist, den viele Anfänger-Expositionen verwenden; Wenn Sie in diesem Kontext die Werte in whitespace-separierte Tokens aufteilen möchten, würde dies ein Skript verwenden.Ich stimme zu, dass, wenn Sie sich direkt auf die Positionsparameter in einem Skript beziehen müssen, "$ @" fast immer das ist, was Sie wollen. – tripleee

+0

Mit zum Beispiel 'set - 'abc def' ghi',' für arg in "$ @"; echo "$ arg"; done' macht das Richtige. Diese tun selten das Richtige: '$ *' oder '$ *" '(selten = nur wenn Sie die Argumente reduzieren wollen). Es macht keinen Sinn, weiterhin Anfänger-Expositionen zu wiederholen, die falsch sind. –

0

Das folgende Beispiel mit Ihrem Eingabedatenstring sollte das Problem mit sed lösen.

$ echo abcderwer 123123 10,200 asdfasdf iopjjop | sed -ne 's/^.*\([0-9,]\{6\}\).*$/\1/p' 
10,200 
4

In reiner Bash:

pattern='([[:digit:]]{2},[[:digit:]]{3})' 
[[ $string =~ $pattern ]] 
echo "${BASH_REMATCH[1]}" 
0

Eine etwas untypische Lösung.

< input tr -cd [0-9,\ ] | tr \ '\012' | grep '^..,...$' 

(Der erste tr entfernt alles außer Komma, Leerzeichen und Ziffern Die zweite tr ersetzt Leerzeichen durch Zeilenumbrüche, setzt jede "Zahl" auf eine separate Zeile, und das Grep verwirft alles außer den, die Ihrem Kriterium entsprechen.)