bash:获取以给定字符串开头的命令列表
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/511683/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
bash: get list of commands starting with a given string
提问by Paolo Tedesco
Is it possible to get, using Bash, a list of commands starting with a certain string?
I would like to get what is printed hitting <tab> twice after typing the start of the command and, for example, store it inside a variable.
是否可以使用 Bash 获取以某个字符串开头的命令列表?
我想在键入命令的开头后两次点击 <tab> 获得打印的内容,例如,将其存储在一个变量中。
回答by Jacob Mattison
You should be able to use the compgencommand, like so:
您应该能够使用compgen命令,如下所示:
compgen -A builtin [YOUR STRING HERE]
For example, "compgen -A builtin l" returns
例如,“compgen -A builtin l”返回
let
local
logout
You can use other keywords in place of "builtin" to get other types of completion. Builtin gives you shell builtin commands. "File" gives you local filenames, etc.
您可以使用其他关键字代替“builtin”来获得其他类型的补全。内置为您提供 shell 内置命令。“文件”为您提供本地文件名等。
Here's a list of actions (from the BASH man page for completewhich uses compgen):
这是一个操作列表(来自使用compgen 的完整的 BASH 手册页):
alias Alias names. May also be specified as -a.
arrayvar Array variable names.
binding Readline key binding names.
builtin Names of shell builtin commands. May also be specified as -b.
command Command names. May also be specified as -c.
directory Directory names. May also be specified as -d.
disabled Names of disabled shell builtins.
enabled Names of enabled shell builtins.
export Names of exported shell variables. May also be specified as -e.
file File names. May also be specified as -f.
function Names of shell functions.
group Group names. May also be specified as -g.
helptopic Help topics as accepted by the help builtin.
hostname Hostnames, as taken from the file specified by the HOSTFILE shell
variable.
job Job names, if job control is active. May also be specified as
-j.
keyword Shell reserved words. May also be specified as -k.
running Names of running jobs, if job control is active.
service Service names. May also be specified as -s.
setopt Valid arguments for the -o option to the set builtin.
shopt Shell option names as accepted by the shopt builtin.
signal Signal names.
stopped Names of stopped jobs, if job control is active.
user User names. May also be specified as -u.
variable Names of all shell variables. May also be specified as -v.
回答by porges
A fun way to do this is to hit M-*(Meta is usually left Alt).
一个有趣的方法是点击M-*(Meta 通常是左 Alt)。
As an example, type this:
例如,键入以下内容:
$ lo
Then hit M-*:
然后打M-*:
$ loadkeys loadunimap local locale localedef locale-gen locate
lockfile-create lockfile-remove lockfile-touch logd logger login
logname logout logprof logrotate logsave look lorder losetup
You can read more about this in man 3 readline; it's a feature of the readlinelibrary.
您可以在 中阅读更多相关信息man 3 readline;这是readline图书馆的特色。
回答by Flame
If you want exactly how bash would complete
如果您想要 bash 将如何完成
COMPLETIONS=$(compgen -c "$WORD")
compgen completes using the same rules bash uses when tabbing.
compgen 使用与 bash 使用 Tab 键时相同的规则来完成。
回答by Johannes Schaub - litb
JacobM's answer is great. For doing it manually, i would use something like this:
JacobM 的回答很棒。为了手动完成,我会使用这样的东西:
echo $PATH | tr : '\n' |
while read p; do
for i in $p/mod*; do
[[ -x "$i" && -f "$i" ]] && echo $i
done
done
The test before the output makes sure only executable, regular files are shown. The above shows all commands starting with mod.
输出前的测试确保只显示可执行的常规文件。上面显示了所有以mod.
回答by Adam Rosenfield
Interesting, I didn't know about compgen. Here a script I've used to do it, which doesn't check for non-executables:
有趣,我不知道compgen。这是我用来做的一个脚本,它不检查非可执行文件:
#!/bin/bash
echo $PATH | tr ':' 'findcmd ^foo # finds all commands beginning with foo
findcmd -i -E 'ba+r' # finds all commands matching the pattern 'ba+r', case insensitively
' | xargs -0 ls | grep "$@" | sort
Save that script somewhere in your $PATH(I named it findcmd), chmod u+wit, and then use it just like grep, passing your favorite options and pattern:
将该脚本保存在您的$PATH(我将其命名为findcmd)中的某个位置chmod u+w,然后像 一样使用它grep,传递您最喜欢的选项和模式:
find -L $(echo $PATH | tr ":" " ") -name 'pattern' -type f -perm -001 -print
回答by dmckee --- ex-moderator kitten
Just for fun, another manual variant:
只是为了好玩,另一个手动变体:
find -L $(echo $PATH | tr ":" " ") -name 'pattern' -type f
\( \
-perm -001 -or \
\( -perm -100 -and -user $(whoami)\) \
\) -print
where patternspecifies the file name pattern you want to use. This will miss commands that are not globally executable, but which you have permission for.
wherepattern指定要使用的文件名模式。这将错过不是全局可执行但您有权限的命令。
[tested on Mac OS X]
[在 Mac OS X 上测试]
Use the -orand -andflags to build a more comprehensive version of this command:
使用-or和-and标志来构建这个命令的更全面的版本:
will pick up files you have permission for by virtue of owning them. I don't see a general way to get all those you can execute by virtue of group affiliation without a lot more coding.
将拾取您因拥有它们而获得许可的文件。我没有看到一种通用的方法来获得所有你可以通过组从属关系而无需更多编码的方法。
回答by Oliver N.
Iterate over the $PATH variable and do ls beginningofword*for each directory in the path?
遍历 $PATH 变量并对ls beginningofword*路径中的每个目录执行操作?
To get it exactly equivalent, you would need to filter out only executable files and sort by name (should be pretty easy with ls flags and the sort command).
要使其完全等效,您需要仅过滤掉可执行文件并按名称排序(使用 ls 标志和 sort 命令应该很容易)。
回答by Eduardo
What is listed when you hit are the binary files in your PATH that start with that string. So, if your PATH variable contains: PATH=/usr/local/bin:/usr/bin:/bin:/usr/games:/usr/lib/java/bin:/usr/lib/java/jre/bin:/usr/lib/qt/bin:/usr/share/texmf/bin:.
当您点击时列出的是 PATH 中以该字符串开头的二进制文件。因此,如果您的 PATH 变量包含: PATH=/usr/local/bin:/usr/bin:/bin:/usr/games:/usr/lib/java/bin:/usr/lib/java/jre/bin: /usr/lib/qt/bin:/usr/share/texmf/bin:。
Bash will look in each of those directories to show you the suggestions once you hit . Thus, to get the list of commands starting with "ls" into a variable you could do: MYVAR=$(ls /usr/local/bin/ls* /usr/bin/ls* /bin/ls*) Naturally you could add all the other directories I haven't.
一旦你点击 ,Bash 将查看这些目录中的每一个以向你显示建议。因此,要将以“ls”开头的命令列表放入变量中,您可以执行以下操作: MYVAR=$(ls /usr/local/bin/ls* /usr/bin/ls* /bin/ls*)添加我没有的所有其他目录。

