捕获 bash 内置的多行输出

Ale*_*x B 7 bash shell-builtin

通常,bash 能够分配命令的多行输出:

L=`ls`
Run Code Online (Sandbox Code Playgroud)

这适用于交互式 shell 和脚本。但似乎无法在变量中捕获内置函数的输出:

L=`dirs -l -p`
Run Code Online (Sandbox Code Playgroud)

这在交互式 shell 中有效,但在脚本中只有第一行在变量中结束,可能是由于 bash 对内置函数的不同处理。

为什么会发生这种情况,我该如何做我需要的事情?

msw*_*msw 7

There seems to be some ambiguity in the way that you worded your question. You said:

but in the script only first line end up in the variable

and then your comments suggest that you are writing a shell function - not a script.

我怀疑您知道脚本对于更改目录没有用,因为cd脚本中的任何内容都不会传播到上级 shell。如果您确实尝试在脚本中开发目录更改器,那么您将遇到困难,因为从属 shell不会继承目录堆栈:

$ dirs -l
/home/msw /home/msw/Ubuntu One /home/msw /usr/bin /usr/local /bin /usr/local
$ cat > dirs.sh
dirs -l 
$ bash dirs.sh
/home/msw
Run Code Online (Sandbox Code Playgroud)

你可以得到一个函数来帮助:

$ function passdirs() { bash ndirs.sh `dirs -l -p`; }
$ cat > ndirs.sh
echo $#
echo "$@"
$ passdirs
8
/home/msw /usr/local /usr/bin /bin /usr/local /usr/bin /bin /home/msw
Run Code Online (Sandbox Code Playgroud)

但是,当然,您还需要该函数来影响cd当前 shell 中的

$ function cd_pattern() {
   cd $(dirs -l -p | grep --max-count=1 -e "$1") ; dirs
}
$ dirs
~ /usr/local /bin /usr/share/doc/evince ~/Ubuntu One
$ cd_pattern v..c
/usr/share/doc/evince /usr/local /bin /usr/share/doc/evince ~/Ubuntu One
Run Code Online (Sandbox Code Playgroud)

它也改用$(...)作为反引号的同义词以减少引用混淆。