[英]Bash string interpolation without subshell
我有这样的功能
print_stuff_and_set_vars() {
IMPORTANT_VAL_1=""
IMPORTANT_VAL_2=""
echo -n "some stuff"
echo -n "some more stuff"
echo -n "result"
}
我这样称呼它:
my_main_func() {
print_stuff_and_set_vars
print_stuff_and_set_vars
print_stuff_and_set_vars
echo "IMPORTANT_VAL_1 was $IMPORTANT_VAL_1"
}
相反,我想将所有回显的结果保存到一个字符串中
my_main_func() {
# doesn't work -- result is empty
result="${print_stuff_and_set_vars}${print_stuff_and_set_vars}${print_stuff_and_set_vars}"
echo "the result length was ${#result}"
echo "$result"
echo "IMPORTANT_VAL_1 was $IMPORTANT_VAL_1"
}
如果我使用$()
而不是${}
来启动子shell,这确实有效,但是没有设置全局变量。
有没有办法在不启动子shell的情况下将函数的结果保存到字符串中? 我知道在这个例子中显而易见的答案是将“结果”保存到全局变量而不是回显它,但在我的实际脚本中需要大量更改,如果可能的话我想避免它。
实际上,我只需要知道长度,所以如果有一种方法可以跟踪自函数启动以来打印了多少也可以正常工作。 如果这也zsh
,我实际上也在使用zsh
。
假设函数print_stuff_and_set_vars
的输出不包含换行符,如何:
mkfifo p # create a named pipe "p"
exec 3<>p # open fd 3 for both reading and writing
rm p # now "p" can be closed
print_stuff_and_set_vars() {
IMPORTANT_VAL_1="foo"
IMPORTANT_VAL_2="bar"
echo -n "some stuff "
echo -n "some more stuff "
echo -n "result "
}
my_main_func() {
print_stuff_and_set_vars 1>&3 # redirect to fd 3
print_stuff_and_set_vars 1>&3 # same as above
print_stuff_and_set_vars 1>&3 # same as above
echo 1>&3 # send newline as an end of input
IFS= read -r -u 3 result # read a line from fd 3
echo "the result length was ${#result}"
echo "$result"
echo "IMPORTANT_VAL_1 was $IMPORTANT_VAL_1"
}
my_main_func
exec 3>&- # close fd 3
输出:
the result length was 102
some stuff some more stuff result some stuff some more stuff result some stuff some more stuff result
IMPORTANT_VAL_1 was foo
使用临时文件很容易做到这一点。 例子:
print_stuff_and_set_vars() {
IMPORTANT_VAL_1="x"
IMPORTANT_VAL_2="y"
echo -n "some stuff"
echo -n "some more stuff"
echo -n "result"
}
print_stuff_and_set_vars > /tmp/$$
myVar=$(< /tmp/$$)
echo $myVar
echo $IMPORTANT_VAL_1
echo $IMPORTANT_VAL_2
也可以使用命名管道或文件描述符来实现这一点。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.