pushd, popd vs cd, cd- в bash и zsh

16

Есть ли разница между поведением pushd / popd в bash и zsh? Похоже, в zsh cd, cd ведет себя точно так же, как pushd / popd (который автоматически добавляет / pops каталог, когда cd), тогда как в bash cd не влияет на стек dir.

Если кто-то может дать мне указатель, это было бы здорово.

dragonxlwang
источник
Я могу говорить только с bash: использование cdустанавливает переменную оболочки OLDPWDв предыдущий каталог и cd -переводится в cd "$OLDPWD".
Гленн Джекман
@glennjackman, спасибо. Означает ли это, что в bash cd нечего делать с push / popd?
dragonxlwang
Я только что проверил, а pushdтакже устанавливаетOLDPWD
Гленн Джекман
И dirstack, возвращенный dirsвсегда держит PWD в качестве первого элемента
Гленн Джекман
да, но это также имеет большой смысл, если cd не касается стеков dir, которыми управляет pushd / popd в bash.
dragonxlwang

Ответы:

17

По-разному. В zshвы можете настроить , cdчтобы нажать на старый каталог на каталог стека автоматически, но это не по умолчанию.

Насколько я могу судить, zshнастройки по умолчанию ведут себя очень похоже на bash:

  • cd somedir
    • изменить каталог на somedir
    • сохранить исходный каталог в OLDPWD
    • устанавливать PWD="somedir"
    • заменить верхний элемент стека каталогов (как показано dirs) на somedir(количество элементов в стеке не меняется).
  • cd -:
    • изменить каталог на $OLDPWD
    • поменять значения PWDиOLDPWD
    • изменить верхний элемент стека каталогов, чтобы отразить (новый) PWD
  • pushd somedir:
    • изменить каталог на somedir
    • сохранить оригинальный каталог в OLDPWD
    • устанавливать PWD="somedir"
    • протолкнуть somedirв стек каталога (расширяя его на один элемент)
  • popd:
    • сохранить оригинальный каталог в OLDPWD
    • удалить первый элемент из стека каталогов
    • изменить каталог на новый верхний элемент стека каталогов
    • установить PWDновый верхний элемент стека каталогов

Примечание: считается ли текущий рабочий каталог элементом стека каталогов, отличается от zshи bash. Я использовал в bashкачестве ссылки для приведенных выше списков.

  • В bashнастоящее время рабочий каталог считается верхним элементом стека каталогов. The man 1 bashговорит:

    pushd [-n] [dir]

    […] Добавляет dirв стек каталогов вверху, делая его новым текущим рабочим каталогом, как если бы он был предоставлен в качестве аргумента для cdвстроенной функции. [...]

    Печать DIRSTACK( echo ${dirstack[@]}) подтверждает, что первый элемент идентичен $PWD.

  • В zshнастоящее время рабочий каталог не является частью стека каталогов (но все равно показан с помощью dirs). man 1 zshbuiltinsговорит:

    pushd [ -qsLP ] [ arg ]

    […] Измените текущий каталог и поместите старый текущий каталог в стек каталогов. В первой форме измените текущий каталог на arg. [...]

    Печать dirstack( echo ${dirstack[@]}) и сравнение ее с выводом команды dirsдолжны показать, что PWDона не является частью `dirstack.

В обеих оболочках dirsпечатается текущий рабочий каталог как первый элемент. Также в обеих оболочках элемент стека каталога с индексом 1относится к каталогу, который был текущим до последнего pushd. Это потому, что массивы в zshобычно нумеруются из 1, в то время как они нумеруются из 0в bash. Таким образом, есть небольшая практическая разница


Как сказано выше, это поведение может быть изменено в zsh.

Если вы устанавливаете AUTO_PUSHDопцию в zsh( setopt autopushd) cd somedirведет себя как pushd somedir, предыдущий каталог автоматически помещается в стек каталогов. Это, вероятно, случай на вашей машине. Вы можете запустить, setoptчтобы получить список параметров, которые не установлены по умолчанию. Видите, autopushdпоявляется ли в списке.

Но это не меняет cd -поведение popd. Вместо этого он просто помещается $PWDв стек каталогов и меняет каталог на $OLDPWD. Это означает, что повторные вызовы на cd -самом деле увеличивают стек каталогов ( ($PWD $OLDPWD $PWD $OLDPWD $PWD …)). Если он действительно ведет себя так же, как popdв вашей системе, я бы предложил, если cdэто на самом деле встроенный ( whence -v cd); возможно, его заменили псевдонимом или функцией.

Поскольку стек каталогов будет довольно быстро расти при AUTO_PUSHDвключенном, вы можете ограничить его размер, установив для параметра DIRSTACKSIZEжелаемый максимальный размер.
Вы также можете предотвратить дублирование, установив PUSHD_IGNORE_DUPSпараметр.
Для большего количества вариантов посмотрите руководство .

Adaephon
источник
Какова цель стека каталогов, кроме как посмотреть на него через dirs?
Xerus
@Xerus Позволяет вернуться к ранее посещенным каталогам popdбез необходимости набирать (или даже знать) путь.
Adaephon