PS1 = '$ (pwd)' Warum funktioniert das und warum unterscheidet sich das von PS1 = $ (pwd)

18

Warum wechselt die Eingabeaufforderung bei Eingabe dieses Befehls in mein Verzeichnis?

PS1='$(pwd)'

Ich verwende einfache Anführungszeichen, was keine Interpolation bedeutet, auch bekannt als echo '$(pwd)'- →$(pwd)

Sagen Sie außerdem, dass wir geklärt haben, warum dies funktioniert. Warum funktioniert es anders als PS1=$(pwd)? (überhaupt keine Anführungszeichen)

Mit "anders" meine ich, dass wenn ich die Anführungszeichen verwende, die Eingabeaufforderung weiterhin in mein aktuelles Verzeichnis wechselt, während ich durch das Terminal navigiere. Wenn ich jedoch keine Anführungszeichen verwende, bleibt die Eingabeaufforderung immer das Verzeichnis, in dem ich mich befunden habe, als ich den Befehl zum ersten Mal eingegeben habePS1=$(pwd)

Warum?

HashWizard
quelle
2
Speichern Sie einige CPU-Zyklen und verwenden Sie die entsprechende PS1 = '$ PWD'
jlliagre

Antworten:

29

Wenn Sie einer Variablen einfach einen Wert zuweisen, wird der $(...)Ausdruck ausgewertet, es sei denn, er wird in einfache Anführungszeichen eingeschlossen (oder mit einem umgekehrten Schrägstrich versehen). Um dies zu verstehen, versuchen Sie, diese beiden zu vergleichen:

A=$(pwd)
echo "$A"
B='$(pwd)'
echo "$B"

Der Wert von wird Asofort zur Zeichenfolge /home/yourusernameund es wird offensichtlich nicht gespeichert, woher diese Zeichenfolge stammt. Er bleibt auch dann gleich, wenn Sie das Verzeichnis wechseln. Der Wert von Bwird jedoch zur Literalzeichenfolge, $(pwd)ohne interpretiert zu werden.

Nun wird in den Wert von PS1etwas Besonderes geschieht: immer dann , wenn die Aufforderung gedruckt wird, bestimmte spezielle Konstrukte , interpretiert werden, zum Beispiel der Befehl Substitution $(...)wird durchgeführt , genau so , wie es oben in die an der Zuordnung passiert Avariabel. Es ist offensichtlich, dass es keine Möglichkeit gibt, dies zu ändern, wenn Ihr PS1den Literal-String Ihres Home-Verzeichnisses enthält (wie oben mit A). Wenn es jedoch die Zeichenfolge enthält $(pwd)(wie oben mit B), wird sie jedes Mal ausgewertet, wenn die Eingabeaufforderung gedruckt wird, und daher wird Ihr tatsächliches Verzeichnis angezeigt.

egmont
quelle
14

Sowohl in bash als auch in zsh wird der Wert von PS1nicht als Eingabeaufforderung verwendet, da er einige Erweiterungen durchläuft. Die Regeln unterscheiden sich für die beiden Schalen, aber in beiden Fällen eine des Schrittes „Dollar“ Erweiterungen (variable Substitution, Befehl Substitutionen, arithmetische Auswertung) mit der gleichen Syntax wie in normaler Shell - Syntax (auszuführen , , oder , , ) .$VARIABLE${VARIABLE}$(COMMAND)`COMMAND`$((EXPRESSION))$[EXPRESSION]

  • In Bash ist die Dollar-Erweiterung standardmäßig aktiviert, kann jedoch mit deaktiviert werden shopt -u promptvars.
  • In zsh ist die Dollar-Erweiterung standardmäßig deaktiviert, aber viele Benutzer (und die meisten Konfigurations-Frameworks, die Sie im Web finden) aktivieren sie mit setopt prompt_subst.

Mit Dollar - Expansion in der Eingabeaufforderung eingeschaltet wird , PS1='$(pwd)'setzte PS1auf den 6-Zeichenwert $(pwd)und verursacht somit $(pwd)ausgewechselt werden, und daher der pwdBefehl ausgeführt wird jedesmal , wenn die Schale zeigt eine neue Aufforderung. Auf der anderen Seite, PS1=$(pwd)setzt PS1auf dem, was ist die aktuelle Arbeitsverzeichnis der Shell an der Zeit. Wenn Sie die Dollar-Erweiterung ausgeschaltet PS1='$(pwd)'hätten, würde dies dazu führen, dass die Eingabeaufforderung die wörtliche Zeichenfolge ist $(pwd).

Beachten Sie, dass es bequemere Möglichkeiten gibt, das Arbeitsverzeichnis in der Eingabeaufforderung abzurufen:

  • In Bash, mit einem Backslash-Escape wie \w, das Ihr Home-Verzeichnis auf abkürzt ~und durch Einstellen gekürzt werden kann PROMPT_DIRTRIM.
  • In zsh mit einem entkommen Prozent wie %/oder%~ ( %/ist das gleiche wie $PWD, %~Home - Verzeichnisse abkürzt), die eine Trimmeinstellung hat.
  • $PWDEntspricht in beiden Shells (und allen anderen Bourne-ähnlichen Shells) $(pwd): Sie müssen keinen Unterprozess ausführen, um das aktuelle Arbeitsverzeichnis abzurufen.
Gilles 'SO - hör auf böse zu sein'
quelle
7

Denn ohne die Anführungszeichen wird das $ (pwd) ausgewertet, wenn PS1 eingestellt wird. Mit den Anführungszeichen wird die Bewertung von $ (pwd) verschoben, bis die Eingabeaufforderung angezeigt wird.

Ohne die Anführungszeichen wird PS1 zum Zeitpunkt der Einstellung von PS1 auf das aktuelle Verzeichnis gesetzt. Mit den einfachen Anführungszeichen wird PS1 auf $ (pwd) gesetzt, was bedeutet, dass das aktuelle Verzeichnis jedes Mal ausgewertet und gedruckt wird, wenn die Eingabeaufforderung angezeigt wird.

farhangfarhangfar
quelle