如何在 shell 脚本中执行命令而不打开新 shell

如何在 shell 脚本中执行命令而不打开新 shell

我想在 shell 脚本内执行命令并将其存储在变量中,但它正在打开一个我不想要的新 shell。有什么办法可以纠正这个问题吗?这是我的脚本。

#!/bin/bash
V1=`<any_command>`      #The shell should not open a new shell
V2=`<another_command>`  #The shell should not open a new shell

我可以像下面一样执行 shell 脚本以在同一个 shell 上执行:

. ./Script.sh

但是如果 shell 脚本中有命令要存储在变量中,为此我使用

V1=`<any_command>` 

这仍然会打开一个新的外壳,这是我不想要的。

答案1

如果将命令的输出存储在变量中,则该命令将在变量中执行子外壳。这是无法逃避的。如果您想要保留 shell 上下文中的更改(变量、重定向等)并捕获输出,则需要以不同的方式组织脚本。

一种方法是使用临时文件。这是可移植的(可以在任何 POSIX sh 中工作,除了创建临时文件的方式不是 POSIX)和非侵入性的(您可以将其视为any_command黑匣子,不必修改它)。

unset tmp1
trap 'rm -f "$tmp1"' EXIT INT TERM HUP
tmp1="$(mktemp)"
any_command >"$tmp1"
V1=$(cat "$tmp1")
rm "$tmp1"

避免使用临时文件的一种可移植但侵入性的方法是进行更改,any_command以便将其输出收集在变量中。这需要将每个外部命令调用附加到该变量。如果有函数调用,这尤其麻烦,因为需要更改函数的代码。例子:

f () {
  echo "$1"
  a=$((a+$1))
  echo "$2"
}
V1=$(f 4 2)

是要改为

f_into_V1 () {
  V1="${V1}${1}"
  a=$((a+$1))
  V1="${V1}${2}"
}
f_into_V1 4 2

相关内容