Wenn Sie GNU grep haben, können Sie mit seiner -o
Option nach einem regulären Ausdruck suchen und nur den passenden Teil ausgeben. (Andere grep-Implementierungen können nur die gesamte Zeile anzeigen.) Wenn sich mehrere Übereinstimmungen in einer Zeile befinden, werden sie in separaten Zeilen gedruckt.
grep -o '\[[0-9]*\]'
Wenn Sie nur die Ziffern und nicht die Klammern wollen, ist es etwas schwieriger; Sie müssen eine Behauptung mit der Breite Null verwenden: einen regulären Ausdruck, der mit der leeren Zeichenfolge übereinstimmt, jedoch nur, wenn eine Klammer vor bzw. nach dieser steht. Zusicherungen ohne Breite sind nur in Perl-Syntax verfügbar.
grep -P -o '(?<=\[)[0-9]*(?=\])'
Bei sed müssen Sie den Druck mit ausschalten -n
und die gesamte Zeile abgleichen und nur den passenden Teil behalten. Wenn mehrere Übereinstimmungen in einer Zeile möglich sind, wird nur die letzte Übereinstimmung gedruckt. Weitere Informationen zur Verwendung von sed finden Sie unter Extrahieren eines Regex, der mit "sed" übereinstimmt, ohne die umgebenden Zeichen zu drucken .
sed -n 's/^.*\(\[[0-9]*\]\).*/\1/p'
oder wenn Sie nur die Ziffern und nicht die Klammern wollen:
sed -n 's/^.*\[\([0-9]*\)\].*/\1/p'
Ohne grep -o
ist Perl das Werkzeug der Wahl, wenn Sie etwas wollen, das sowohl einfach als auch verständlich ist. -n
Enthält die Zeile in jeder Zeile ( ) eine Übereinstimmung für \[[0-9]*\]
, geben Sie diese Übereinstimmung ( $&
) und eine neue Zeile ( -l
) aus.
perl -l -ne '/\[[0-9]*\]/ and print $&'
Wenn Sie nur die Ziffern verwenden möchten, setzen Sie Klammern in den regulären Ausdruck, um eine Gruppe abzugrenzen, und drucken Sie nur diese Gruppe.
perl -l -ne '/\[([0-9]*)\]/ and print $1'
PS Wenn Sie nur eine oder mehrere Ziffern in Klammern benötigen, wechseln Sie [0-9]*
zu [0-9][0-9]*
oder zu [0-9]+
in Perl.
[number]
" bedeutet außer[0-9]
perl
Regex-Behauptungen sehen wirklich nützlich aus! Ich habe darüber gelesen, nachdem Sie gesehen haben, dass Sie sowohl Rückwärts- als auch Vorwärtsaussagen verwenden, auch in grep (ich habe die Tatsache ausgeschaltet, dass Sie eine Regex-Engine auswählen können). Ich werde von jetzt an etwas mehr Zeit für Perls Regex verwenden. Danke ... PS .. Ich habe gerade gelesenman grep
... "Dies ist sehr experimentell und grep -P kann vor nicht implementierten Funktionen warnen." ... ich hoffe das heißt nicht instabil (?) ...Sie können es nicht mit tun
cut
.tr -c -d '0123456789\012'
sed 's/[^0-9]*//g'
awk -F'[^0-9]+' '{ print $1$2$3 }'
grep -o -E '[0-9]+'
tr
ist die natürlichste Lösung für das Problem und würde wahrscheinlich am schnellsten laufen, aber ich denke, Sie würden gigantische Eingaben benötigen, um eine dieser Optionen in Bezug auf die Geschwindigkeit zu trennen.quelle
^.*
ist gierig und verbraucht alles außer der letzten Ziffer und+
muss sein\+
oder sonst die Posix verwenden\([0-9][0-9]*\)
.... und's/[^0-9]*//g'
funktioniert auf jeden Fall genauso gut,... Thanks for the
tr -c` Beispiel, aber ist das nicht\012
überflüssig?\012
: es wird benötigt, sonsttr
werden die Zeilenumbrüche essen.\0
,1
,2
(oder sogar \, 0, 1, 2). Ich bin nicht gut genug auf Oktal eingestellt, wie es scheint. Danke.Wenn Sie meinen, einen Satz aufeinanderfolgender Ziffern zwischen nichtstelligen Zeichen zu extrahieren, denke ich
sed
und binawk
der Beste (obwohlgrep
er Ihnen auch die übereinstimmenden Zeichen geben kann):sed
: Sie können natürlich die Ziffern abgleichen, aber es ist vielleicht interessant, das Gegenteil zu tun und die nicht-Ziffern zu entfernen (funktioniert, solange es nur eine Ziffer pro Zeile gibt):grep
: Sie können aufeinanderfolgende Ziffern abgleichenIch gebe kein Beispiel dafür,
awk
weil ich keine Erfahrung damit habe; Es ist interessant zu bemerken, dass dies, obwohlsed
es sich um ein Schweizer Messer handelt,grep
einfacher und besser lesbar ist. Dies funktioniert auch für mehr als eine Zahl in jeder Eingabezeile (es werden-o
nur die jeweils passenden Teile der Eingabe gedruckt) in eigener Zeile):quelle
sed
eqivalent des „mehr als eine Nummer pro Zeile“ Beispielsgrep -o '[[:digit:]]*'
. . .sed -nr '/[0-9]/{ s/^[^[0-9]*|[^0-9]*$//g; s/[^0-9]+/\n/g; p}'
... (+1)Da gesagt wurde, dass dies nicht möglich ist
cut
, werde ich zeigen, dass es leicht möglich ist, eine Lösung zu finden, die zumindest nicht schlechter ist als einige der anderen, auch wenn ich die Verwendungcut
als "Beste" nicht befürworte. (oder sogar eine besonders gute) Lösung. Es sollte gesagt werden, dass jede Lösung, die nicht speziell nach*[
und]*
um die Ziffern sucht, vereinfachende Annahmen macht und daher dazu neigt, bei Beispielen zu scheitern, die komplexer sind als die vom Fragesteller angegebenen (z. B. Ziffern außerhalb von*[
und]*
, die nicht gezeigt werden sollten). Diese Lösung überprüft mindestens die Klammern und kann erweitert werden, um auch die Sternchen zu überprüfen (als Übung für den Leser):Hierbei wird die
-d
Option verwendet, die ein Trennzeichen angibt. Natürlich können Sie auch in dencut
Ausdruck einfügen, anstatt aus einer Datei zu lesen. Währendcut
wahrscheinlich ziemlich schnell, da es einfach (kein Regex - Engine) ist, müssen Sie es mindestens zweimal (oder ein paar mehr Zeit zu überprüfen aufrufen*
), die einen Prozess Overhead erzeugt. Der eigentliche Vorteil dieser Lösung besteht darin, dass sie besonders für Gelegenheitsanwender, die sich mit Regex-Konstrukten nicht auskennen, gut lesbar ist.quelle