Frage Was ist "-bash:!": Ereignis nicht gefunden "


Versuchen Sie Folgendes unter einer Bash-Shell auszuführen echo "Reboot your instance!"

Auf meiner Installation:

root@domU-12-31-39-04-11-83:/usr/local/bin# bash --version
GNU bash, version 4.1.5(1)-release (i686-pc-linux-gnu)
Copyright (C) 2009 Free Software Foundation, Inc.
License GPLv3+: GNU GPL version 3 or later <http://gnu.org/licenses/gpl.html>

This is free software; you are free to change and redistribute it.
There is NO WARRANTY, to the extent permitted by law.
root@domU-12-31-39-04-11-83:/usr/local/bin# uname -a
Linux domU-12-31-39-04-11-83 2.6.35-22-virtual #35-Ubuntu SMP Sat Oct 16 23:57:40 UTC 2010 i686 GNU/Linux
root@domU-12-31-39-04-11-83:/usr/local/bin# echo "Reboot your instance!"
-bash: !": event not found

Kann mir bitte jemand erklären, was "Bash-Events" sind? Ich habe dieses Konzept noch nie zuvor gehört. Wie soll ich "!" Ausgeben? am Ende des Satzes?


88
2017-12-02 10:45


Ursprung




Antworten:


Sie können die Geschichtssubstitution mit deaktivieren set +H.


40
2017-12-02 16:31



Kennen Sie die Gründe für die Syntax? Es scheint wirklich kontra intuitiv. Du würdest denken, du würdest tippen +H etwas ermöglichen und -H um etwas zu deaktivieren. - PunkyGuy
@PunkyGuy: Ich weiß nicht, die Geschichte (Wortspiel beabsichtigt) dahinter, aber Unix-Optionen beginnen in der Regel mit einem Bindestrich (oder Minus) und + ist einfach das Gegenteil davon. - Dennis Williamson


! ist ein Sonderzeichen für bash, es wird verwendet, um auf vorherige Befehle zu verweisen; z.B,

!rm

ruft den letzten Befehl ab, der mit der Zeichenfolge "rm" begonnen hat, und führt ihn aus

!rm:p

wird den letzten Befehl, der mit der Zeichenfolge "rm" begonnen hat, abrufen, aber nicht ausführen. bash interpretiert das Ausrufezeichen in echo "reboot your instance!" wie "Ersetzen Sie hier den letzten Befehl, der mit den Zeichen begann, die unmittelbar auf das Ausrufezeichen folgten"und schimpft auf dich, dass es kein Ereignis (Befehl) in deiner Geschichte finden kann, das mit einem einzigen doppelten Zitat begann.

Versuchen

echo reboot your instance\!

das Ausrufezeichen vor bash schützen (fliehen).


86
2017-12-02 10:49



Ja, aber sollte passieren, wenn ich Echo -e "einige Text $ ENV_VAL etwas mehr Text \ nReboot jetzt verwenden möchte!" ? - Maxim Veksler
Schreibe zwei Echo-Anweisungen; Sie erhalten den Zeilenvorschub kostenlos. - MadHatter
Einfache Lösung besteht darin, einfache Anführungszeichen und doppelte Anführungszeichen gleichzeitig zu verwenden: echo -e "Text \ nReeboot" '!' - mmey
Das ist scheiße. Wenn ich dem Ausrufezeichen nicht entgehe, wirft Bash einen Anfall. Wenn ich tun es zu entkommen, ist der Backslash in der letzten Zeichenfolge enthalten. Warum machst du das, Bash !! (pastebin.com/g4PYv56A) - Hubro
@Hubro in Fairness, ich bin mir nicht sicher, das ist alles Bashs Schuld. Sie haben etwas komplizierter, indem Sie Ruby verwenden, um Dinge zu bash zu füttern, und es ist mir nicht klar, welchen Teil Ruby beim Entfernen oder Verstärken von Escape-Charakteren spielt. - MadHatter


Um das ursprüngliche Problem zu lösen, verwenden Sie einfache Anführungszeichen anstelle von Anführungszeichen. Mit letzterem versucht bash, bestimmte Zeichen zu erweitern, bevor das Ergebnis an den Befehl übergeben wird (in diesem Fall echo). Mit einfachen Anführungszeichen übergibt bash den gesamten String unverändert.

! wird in Befehlen verwendet, um auf den Befehlszeilenverlauf zu verweisen. Sehen: http://tldp.org/LDP/abs/html/abs-guide.html#HISTCOMMANDS für einen vollen Satz. Mit dem obigen Beispiel versucht bash zu expandieren !" als Verweis auf ein Ereignis, bevor Echo eingesehen wird, daher der Fehler.

Beachten Sie, dass in Skripten alles Die History-Befehle sind deaktiviert, da sie nur in einer interaktiven Shell sinnvoll sind.

Der einzige, den ich regelmäßig benutze, ist !$. Es wird bis zum letzten Argument des vorherigen Befehls erweitert. Es ist eine nützliche Kurzschrift an Orten.


22
2017-12-02 11:02



!! den letzten eingegebenen Befehl vollständig einzugeben, ist bemerkenswert nützlich; insbesondere, sudo !! oder pfexec !! - jgoldschrafe
Ich finde auch, dass sudo und pfexec nette Dienstprogramme sind, aber nicht so begeistert sein müssen. - LeartS
$_ funktioniert in mehr Shells als Bash und es ist eine richtige Variable, im Gegensatz !$. (und @Learts: Ich mochte den Witz deines Witzes Mangel an Emoticons.;)) - ΤΖΩΤΖΙΟΥ


Setzen Sie einfach einen Abstand zwischen! und "als es funktioniert.

Prost.


5
2017-09-25 07:06



Könnten Sie bitte eine Erklärung hinzufügen, warum Ihre Lösung funktioniert? - 200_success
Das funktioniert, weil Bash nur behandelt! als Sonderzeichen, wenn direkt ein Nicht-Leerzeichen folgt. Es wird jedoch auch ein zusätzliches Leerzeichen zu Ihrer Ausgabe hinzufügen, so dass dies nicht immer gewünscht ist ... - mmey


Ja, ! ist ein Sonderzeichen für bash, es wird verwendet, um auf vorherige Befehle zu verweisen.

Nur wenige Möglichkeiten, wie Sie mit der Situation umgehen können

Der folgende Befehl gibt die Zeichenfolge so aus, wie sie ist

echo 'Reboot your instance!'

Der folgende Befehl führt den Befehl aus und verkettet die Zeichenfolge

echo 'escaping #'" adding `which python` to the string"
echo '#!'`which python`

2
2018-04-25 13:57





Im bash 4.3 Es scheint, dass Sie keine einfachen Anführungszeichen mehr verwenden müssen set +H:

$ bash --version
GNU bash, version 4.3.46(1)-release (x86_64-unknown-linux-gnu)
[...]
$ echo "Reboot your instance!"
Reboot your instance!

1
2017-07-12 14:43



Wahrscheinlich ein Bug, denn hier habe ich 4.4.12 und noch einmal, ich brauche set +H oder zitieren. Oder du hast set +H irgendwo (wie in /etc/profile). - Bodo Thiesen
Die Verwendung von! -Char, nicht am Ende des Satzes, bestätigt, dass die Ereigniserkennung von bash immer noch gut funktioniert. Version ist 4.3.30 ........ $ echo "Prüfe deinen Satz! Foo" bash:! Foo: Event nicht gefunden - JohnnyD92


Du könntest auch einen benutzen Heredoc:

cat <<EOF
Reboot your instance!
EOF

Es ist in diesem Fall nervig, weil es kein Einzeiler ist, aber für längere Befehle (wie das Schreiben eines Bash-Skripts) funktioniert es großartig.


0
2017-07-07 11:41