Regex mit Anführungszeichen bashen?
Frage
Der folgende Code
number=1
if [[ $number =~ [0-9] ]]
then
echo matched
fi
funktioniert.Wenn ich jedoch versuche, Anführungszeichen im regulären Ausdruck zu verwenden, stoppt es:
number=1
if [[ $number =~ "[0-9]" ]]
then
echo matched
fi
Ich habe es versucht "\[0-9\]"
, zu.Was vermisse ich?
Lustig genug, Leitfaden zur erweiterten Bash-Skripterstellung schlägt vor, dass dies funktionieren sollte.
Bash-Version 3.2.39.
Lösung
Es wurde geändert zwischen 3,1 und 3,2.Ich schätze, der erweiterte Leitfaden muss aktualisiert werden.
Dies ist eine knappe Beschreibung der neuen Funktionen, die BASH-3.2 seit der Veröffentlichung von Bash-3.1 hinzugefügt haben.Wie immer ist die manuelle Seite (doc/bash.1) der Ort, an dem sie nach vollständigen Beschreibungen suchen.
- Neue Funktionen in Bash
schnipsen
F.Zitieren des String-Arguments an den [[Befehls-Operator) erzwingt jetzt die Zeichenfolge, wie bei den anderen Muster-Matching-Operatoren.
Leider werden dadurch vorhandene Zitate mithilfe von Skripten beschädigt, es sei denn, Sie hatten die Einsicht, Muster in Variablen zu speichern und diese anstelle der regulären Ausdrücke direkt zu verwenden.Beispiel unten.
$ bash --version
GNU bash, version 3.2.39(1)-release (i486-pc-linux-gnu)
Copyright (C) 2007 Free Software Foundation, Inc.
$ number=2
$ if [[ $number =~ "[0-9]" ]]; then echo match; fi
$ if [[ $number =~ [0-9] ]]; then echo match; fi
match
$ re="[0-9]"
$ if [[ $number =~ $re ]]; then echo MATCH; fi
MATCH
$ bash --version
GNU bash, version 3.00.0(1)-release (i586-suse-linux)
Copyright (C) 2004 Free Software Foundation, Inc.
$ number=2
$ if [[ $number =~ "[0-9]" ]]; then echo match; fi
match
$ if [[ "$number" =~ [0-9] ]]; then echo match; fi
match
Andere Tipps
Mit Bash 3.2 wurde eine Kompatibilitätsoption compat31 eingeführt, die das Anführungszeichenverhalten für reguläre Bash-Ausdrücke auf 3.1 zurücksetzt
Ohne compat31:
$ shopt -u compat31
$ shopt compat31
compat31 off
$ set -x
$ if [[ "9" =~ "[0-9]" ]]; then echo match; else echo no match; fi
+ [[ 9 =~ \[0-9] ]]
+ echo no match
no match
Mit compat31:
$ shopt -s compat31
+ shopt -s compat31
$ if [[ "9" =~ "[0-9]" ]]; then echo match; else echo no match; fi
+ [[ 9 =~ [0-9] ]]
+ echo match
match
Link zum Patch:http://ftp.gnu.org/gnu/bash/bash-3.2-patches/bash32-039
GNU-Bash, Version 4.2.25(1)-Release (x86_64-pc-linux-gnu)
Einige Beispiele für String-Matches und Regex-Matches
$ if [[ 234 =~ "[0-9]" ]]; then echo matches; fi # string match
$
$ if [[ 234 =~ [0-9] ]]; then echo matches; fi # regex natch
matches
$ var="[0-9]"
$ if [[ 234 =~ $var ]]; then echo matches; fi # regex match
matches
$ if [[ 234 =~ "$var" ]]; then echo matches; fi # string match after substituting $var as [0-9]
$ if [[ 'rss$var919' =~ "$var" ]]; then echo matches; fi # string match after substituting $var as [0-9]
$ if [[ 'rss$var919' =~ $var ]]; then echo matches; fi # regex match after substituting $var as [0-9]
matches
$ if [[ "rss\$var919" =~ "$var" ]]; then echo matches; fi # string match won't work
$ if [[ "rss\\$var919" =~ "$var" ]]; then echo matches; fi # string match won't work
$ if [[ "rss'$var'""919" =~ "$var" ]]; then echo matches; fi # $var is substituted on LHS & RHS and then string match happens
matches
$ if [[ 'rss$var919' =~ "\$var" ]]; then echo matches; fi # string match !
matches
$ if [[ 'rss$var919' =~ "$var" ]]; then echo matches; fi # string match failed
$
$ if [[ 'rss$var919' =~ '$var' ]]; then echo matches; fi # string match
matches
$ echo $var
[0-9]
$
$ if [[ abc123def =~ "[0-9]" ]]; then echo matches; fi
$ if [[ abc123def =~ [0-9] ]]; then echo matches; fi
matches
$ if [[ 'rss$var919' =~ '$var' ]]; then echo matches; fi # string match due to single quotes on RHS $var matches $var
matches
$ if [[ 'rss$var919' =~ $var ]]; then echo matches; fi # Regex match
matches
$ if [[ 'rss$var' =~ $var ]]; then echo matches; fi # Above e.g. really is regex match and not string match
$
$ if [[ 'rss$var919[0-9]' =~ "$var" ]]; then echo matches; fi # string match RHS substituted and then matched
matches
$ if [[ 'rss$var919' =~ "'$var'" ]]; then echo matches; fi # trying to string match '$var' fails
$ if [[ '$var' =~ "'$var'" ]]; then echo matches; fi # string match still fails as single quotes are omitted on RHS
$ if [[ \'$var\' =~ "'$var'" ]]; then echo matches; fi # this string match works as single quotes are included now on RHS
matches
Wie in anderen Antworten erwähnt, ist das Einfügen des regulären Ausdrucks in eine Variable eine allgemeine Möglichkeit, Kompatibilität zwischen verschiedenen Variablen zu erreichen bash Versionen.Sie können diese Problemumgehung auch verwenden, um dasselbe zu erreichen und dabei Ihren regulären Ausdruck innerhalb des bedingten Ausdrucks zu halten:
$ number=1
$ if [[ $number =~ $(echo "[0-9]") ]]; then echo matched; fi
matched
$