`哪个`,但是全部

`哪个`,但是全部

我认为大多数人都熟悉该which命令,并且我经常使用它。我刚刚遇到了一种情况,我不仅好奇哪个命令在我的路径中第一个,而且好奇有多少个命令以及在哪里全部我所有路径中的命令都是。我尝试了哪个手册页(打字man which让我笑),但没有看到任何东西。

答案1

在某些系统上,which -a显示所有匹配项。如果您的 shell 是 bash 或 zsh1,您可以使用typetype foo显示第一个匹配项并type -a foo显示所有匹配项。这三个命令type,whichwhence做的事情大多相同; shell 和操作系统之间的区别在于可用性、选项以及它们所报告的具体内容。type始终可用,并显示所有可能的类似命令的名称(别名、关键字、shell 内置命令、函数和外部命令)。

显示所有匹配的唯一完全可移植的方法是解析$PATH自己。这是执行此操作的 shell 脚本。如果将其设为 shell 函数,请确保将函数体括在括号中(以便更改为IFSset -f不会转义该函数),然后更改exitreturn.

#!/bin/sh
set -f       # disable globbing
IFS=:        # break words at : only
not_found=1
for d in $PATH; do
  if [ -f "$d/$x" ] && [ -x "$d/$x" ]; then
    printf '%s\n' "$d/$x"
    not_found=0
  fi
done
exit $not_found

或 ksh 93,根据文档,尽管 ksh 93s+ 2008-01-31 仅在我尝试时打印第一个匹配项

答案2

--all 或 -a 标志将显示路径中的所有匹配项和别名(至少在 Fedora、Ubuntu 和 CentOS 上):

which -a which

在 AIX 和 Solaris 上,这将使您接近:

echo "$PATH" | sed -e 's/:/ /g' | \
while read -r p; do find "$p" -type f -name "which"; done

答案3

如果您没有which支持-awhence可用,请自行推出:

#!/bin/sh -f

IFS=":"
for PART in $PATH
do
  if test -x "$PART/$1"
  then
    echo $PART/$1
  fi
done

答案4

ksh 和 zsh 内置了“whence”作为 shell。 whence -a在 zsh 下做你想做的事:

 7:27AM 7 % whence -a cat
/usr/bin/cat
/bin/cat
/usr/bin/cat
/bin/cat

我必须清理 zsh 中的 PATH,其中有很多重复项。whence -a在 ksh 下的工作方式有所不同:

$ whence -a cat
cat is a tracked alias for /usr/bin/cat

我不得不说,这似乎也是一种潜在有用的行为。

相关内容