sed error: "Ungültige Referenz \ 1 auf der RHS des Befehls" s "


103

Ich führe mehrere Substitutionsbefehle als Kern eines Kolorierungsskripts für Maven aus . Einer der sedBefehle verwendet einen regulären Ausdruck, der wie hier beschrieben in der Shell gefunden wird . Die aktuelle (nicht funktionierende) Implementierung finden Sie hier .

Wenn ich eine der Varianten des Befehls in das Skript einbinde, tritt ein anderes Verhalten auf:

Variante 1:

$ sed -re "s/([a-zA-Z0-9./\\ :-]+)/\1/g"

An das Skript angepasst:

-re "s/WARNING: ([a-zA-Z0-9./\\ :-]+)/${warn}WARNING: \1${c_end}/g" \

Fehler: Die Shell gibt die gleichen Informationen aus, als würde ich tippen $ sed. Seltsam!?


Variante 2:

$ sed -e "s/\([a-zA-Z0-9./\\ :-]\+\)/\1/g"

An das Skript angepasst:

-e "s/WARNING: \([a-zA-Z0-9./\\ :-]\+\)/${warn}WARNING: \1${c_end}/g" \

Error:

sed: -e Ausdruck # 7, char 59: ungültige Referenz \ 1 auf der RHS des Befehls 's'


10
In meinem Fall hatte ich eine -i(Option zum Bearbeiten an Ort und Stelle) mit kombiniert -re, was dazu führte -ire(dass -idas reFragment als SUFFIXArgument verwendet wurde und daher der erweiterte Regex-Modus nicht aktiviert wurde). Ändern Sie es, um -i -redas Problem zu beheben.
Janaka Bandara

Es ist auch zu beachten, dass einfache 'und doppelte Anführungszeichen "leicht unterschiedlich behandelt werden, insbesondere beim Dolmetschen $vars. Zum Beispiel: sudo sh -c "sed -r -i 's/(^.+_supplicant.conf)/\1${MTXT}/' /etc/network/interfaces"funktioniert, aber: sudo sh -c 'sed -r -i "s/(^.+_supplicant.conf)/\1${MTXT}/" /etc/network/interfaces'nicht.
not2qubit

Antworten:


51

Müssen Sie nicht tatsächlich erfassen, damit das funktioniert? dh für Variante 2:

-r -e "s/WARNING: (\([a-zA-Z0-9./\\ :-]\+\))/${warn}WARNING: \1${c_end}/g" \

(Hinweis: ungetestet)

Ohne das Argument -r funktionieren Rückverweise (wie \ 1) nicht.


42
Die -rOption zum Sedieren scheint notwendig zu sein, damit der Rückverweis funktioniert. ZB sed -e 's/([[:digit:]])/is a digit/'funktioniert aber sed -e 's/([[:digit:]])/\1 is a digit/erzeugt den ursprünglichen Fehler ohne -rzu sedieren. HINWEIS: Der erste Aufruf von sed sucht nach einem Literal (<digit>)und ist keine Erfassungsgruppe.
Andrew Falanga

Der Kommentar unter der Antwort ist eigentlich eine Antwort. Vielleicht können Sie Ihre Antwort bearbeiten, um sie wiederzugeben.
Miroxlav

@ AndrewFalanga Sie sollten Ihren Kommentar als Antwort gepostet haben
Sanmai

2
Trotzdem war mein Fehler, zu verwenden -irestatt zu verwenden -ri.
Bestellangelegenheiten

54

Dieser Fehler tritt häufig bei Klammern auf, die nicht maskiert werden. Entkomme ihnen und versuche es erneut.


Beispielsweise:

/^$/b
:loop
$!{
N
/\n$/!b loop
}
s/\n(.)/\1/g

Sollte vor jeder Klammer mit Backslashes versehen werden:

/^$/b
:loop
$!{
N
/\n$/!b loop
}
s/\n\(.\)/\1/g

6
Achtung, wenn Sie verwenden, müssen -rSie den Klammern nicht entkommen.
Qräbnö

13

Wenn die Option -r/ --regexp-extendednicht angegeben ist, müssen die Erfassungsklammern maskiert werden.


5

Sie müssen /nach dem entkommen.

sed -e "s/\([a-zA-Z0-9.\/\\ :-]\+\)/\1/g"

Oder wenn Sie sich keine Sorgen um die Flucht machen möchten, verwenden Sie |

sed -e "s|\([a-zA-Z0-9./\\ :-]\+\)|\1|g"

BEARBEITEN:

sed -e "s|WARNING: \([a-zA-Z0-9.-/\\ :]+\)|${warn}WARNING: \1${c_end}|g"

Klingt vernünftig. Im Kontext des Skripts funktioniert dies jedoch nicht.
JJD

Es tut uns leid. Die Bearbeitung löst den Fehler aus : sed: -e expression #7, char 58: Invalid range end. Die Antwort von @Denis funktioniert.
JJD

2
Ok, dann +1 für @Denis 'Antwort
Slackmart
Durch die Nutzung unserer Website bestätigen Sie, dass Sie unsere Cookie-Richtlinie und Datenschutzrichtlinie gelesen und verstanden haben.
Licensed under cc by-sa 3.0 with attribution required.