以独特的方式折叠zsh提示符中的目录

eum*_*iro 8 zsh prompt pwd

有没有办法以独特的方式折叠zsh提示符中的当前工作目录,以便我可以将其复制并粘贴到另一个终端,点击TAB并获取原始路径?

假设我们有以下目录:

/adam/devl
/alice/devl
/alice/docs
/bob/docs
Run Code Online (Sandbox Code Playgroud)

如果提示被编程为显示第一个字符,而我在/ b/d,则它是唯一的.另一方面,/ a/d不是唯一的,所以我需要/ ad/d,/ al/de和/ al/do.甚至/ ali/...一旦用户alex出现.

是否有可能直接在zsh中破解它,或者我是否需要编写一个脚本,找到每个父目录的最短唯一开头?

谢谢你的想法!

Ada*_*ian 9

我不知道zsh有这种类型的内置函数,但是如果不使用单个子shell或慢速管道,脚本应该非常容易:

#!/bin/zsh

paths=(${(s:/:)PWD})

cur_path='/'
cur_short_path='/'
for directory in ${paths[@]}
do
  cur_dir=''
  for (( i=0; i<${#directory}; i++ )); do
    cur_dir+="${directory:$i:1}"
    matching=("$cur_path"/"$cur_dir"*/)
    if [[ ${#matching[@]} -eq 1 ]]; then
      break
    fi
  done
  cur_short_path+="$cur_dir/"
  cur_path+="$directory/"
done

printf %q "${cur_short_path: : -1}"
echo
Run Code Online (Sandbox Code Playgroud)

此脚本将输出自动完成工作所需的最短路径.

您可以将其.zshrc作为函数抛出,然后从任何目录运行它.

function spwd {
  paths=(${(s:/:)PWD})

  cur_path='/'
  cur_short_path='/'
  for directory in ${paths[@]}
  do
    cur_dir=''
    for (( i=0; i<${#directory}; i++ )); do
      cur_dir+="${directory:$i:1}"
      matching=("$cur_path"/"$cur_dir"*/)
      if [[ ${#matching[@]} -eq 1 ]]; then
        break
      fi
    done
    cur_short_path+="$cur_dir/"
    cur_path+="$directory/"
  done

  printf %q "${cur_short_path: : -1}"
  echo
}
Run Code Online (Sandbox Code Playgroud)

这是一个实际的视频:

https://asciinema.org/a/0TyL8foqvQ8ec5ZHS3c1mn5LH

或者如果您愿意,还可以输出一些示例:

~/t $ ls
adam  alice  bob  getshortcwd.zsh

~/t $ ls adam
devl

~/t $ ls alice
devl  docs

~/t $ spwd
/h/v/t

~/t $ cd adam/devl

~/t/adam/devl $ spwd
/h/v/t/ad/d

~/t/adam/devl $ cd ../../alice/devl

~/t/alice/devl $ spwd
/h/v/t/al/de

~/t/alice/devl $ cd ../docs

~/t/alice/docs $ spwd
/h/v/t/al/do

~/t/alice/docs $ `spwd` [TAB]
~/t/alice/docs $ /h/v/t/al/do [TAB]
~/t/alice/docs $ /home/vsimonian/t/alice/docs
Run Code Online (Sandbox Code Playgroud)