Wenn Sie zufällig nur versuchen, Angebote für die Wiederverwendung der Shell zu verarbeiten, können Sie dies tun, ohne sie zu entfernen, und es ist auch denkbar einfach:
aq() { sh -c 'for a do
alias "$((i=$i+1))=$a"
done; alias' -- "$@"
}
Diese Funktionsshell setzt ein beliebiges von Ihnen übergebenes arg-Array in Anführungszeichen und erhöht seine Ausgabe pro iterierbarem Argument.
Hier ist es mit ein paar Argumenten:
aq \
"here's an
ugly one" \
"this one is \$PATHpretty bad, too" \
'this one```****```; totally sucks'
AUSGABE
1='here'"'"'s an
ugly one'
2='this one is $PATHpretty bad, too'
3='this one```****```; totally sucks'
Diese Ausgabe ist eine Ausgabe, dashdie in der Regel in sicheren Anführungszeichen steht '"'"'. bashwürde tun '\''.
Das Ersetzen einer Auswahl einzelner Bytes, die keine Leerzeichen oder Nullen enthalten, durch ein anderes Byte ist in einer POSIX-Shell mit $IFSund wahrscheinlich am schnellsten möglich $*.
set -f; IFS=\"\'\`; set -- $var; printf %s "$*"
AUSGABE
"some ""crazy """"""""string ""here
Dort habe ich es einfach printfso, dass man es sehen kann, aber natürlich, wenn ich es getan hätte:
var="$*"
... und nicht der Wert des printfBefehls $var, den Sie dort in der Ausgabe sehen.
Wenn ich set -fdie Shell anweise, nicht zu globieren - falls die Zeichenfolge Zeichen enthält, die als Glob-Muster ausgelegt werden könnten. Ich mache das, weil der Shells-Parser Glob-Muster erweitert, nachdem er die Feldaufteilung für Variablen durchgeführt hat. Globbing kann wie wieder aktiviert werden set +f. Im Allgemeinen - in Skripten - finde ich es nützlich, meinen Knall wie folgt zu setzen:
#!/usr/bin/sh -f
Und dann explizit das Globbing mit einer set +fbeliebigen Zeile aktivieren , die ich haben möchte.
Die Feldaufteilung erfolgt anhand der Zeichen in $IFS.
Es gibt zwei Arten von $IFSWerten - $IFSLeerzeichen und $IFSNicht-Leerzeichen. $IFSDurch Leerzeichen (Leerzeichen, Tabulatoren, Zeilenvorschübe) getrennte Felder werden so angegeben, dass sie nach der Reihenfolge in ein einzelnes Feld zerlegt werden (oder gar nicht, wenn sie keinem anderen Feld vorangehen) - also ...
IFS=\ ; var=' '; printf '<%s>' $var
<>
Alle anderen sind jedoch so spezifiziert, dass sie pro Vorkommen zu einem einzigen Feld ausgewertet werden - sie werden nicht abgeschnitten.
IFS=/; var='/////'; printf '<%s>' $var
<><><><><>
Alle Variablenerweiterungen sind standardmäßig durch $IFSTrennzeichen getrennte Datenfelder $IFS. Sie werden in separate Felder aufgeteilt . Mit "-quote one überschreiben Sie diese Array-Eigenschaft und werten sie als einzelne Zeichenfolge aus.
Also, wenn ich es tue ...
IFS=\"\'\`; set -- $var
Ich setze das Argumentarray der Shell auf die vielen $IFSbegrenzten Felder, die durch $vardie Erweiterung generiert werden . Wenn es seine konstituierenden Werte für die Zeichen erweitert enthalten in $IFSsind verloren - sie sind jetzt nur Feldtrenn - sie sind \0NUL.
"$*"- Wie bei anderen Variablenerweiterungen in doppelten Anführungszeichen - werden auch die feldaufteilenden Eigenschaften von überschrieben $IFS. Aber zusätzlich , ersetzt es das erste Byte in $IFS für jedes Feld begrenzt in "$@". Also da "wurde der erste Wert in $IFS allen nachfolgenden Begrenzern "in "$*". Und das "muss auch nicht sein, $IFSwenn Sie es teilen. Sie können $IFS after set -- $args vollständig auf einen anderen Wert ändern , und das neue erste Byte wird dann für die Feldbegrenzer in angezeigt "$*". Außerdem können Sie alle Spuren wie folgt entfernen:
set -- $var; IFS=; printf %s "$*"
AUSGABE
some crazy string here
tr. BASHs PE ist gut, aber in diesem Fall ist tr viel schneller. zBecho "$OUTPUT" | tr -dc '[[:alpha:]]'weil Sie nur alphanumerische Zeichen haben möchten