避免在Linux Shell脚本中传递参数和使用命名参数时进行位置引用

时间:2018-08-22 13:01:22

标签: linux bash shell

我有一个脚本“ /tmp/SampleScript.sh”,内容如下:

end 

如果我按以下方式运行此脚本:

echo "First arg: $1"
echo "Second arg: $2"

但是,如果我以以下方式运行它:

[oracle@xxxxx tmp]$ ./SampleScript.sh FirstParamPassed SecondParamPassed
Output Is:
First arg: FirstParamPassed
Second arg: SecondParamPassed

我想要这样的输出:

[oracle@xxxxx tmp]$ ./SampleScript.sh SecondParamPassed FirstParamPassed
Output Is:
First arg: SecondParamPassed
Second arg: FirstParamPassed

如何在REHL Shell脚本中使用这种类型的命名变量。 我已经回答了Is there a way to avoid positional arguments in bash?,但是无法理解如何执行我的情况。

2 个答案:

答案 0 :(得分:1)

请改用环境变量。将脚本编写为

echo "First arg: $FirstParamPassed"
echo "Second arg: $SecondParamPassed"

然后将其命名为

FirstParamPassed=1 SecondParamPassed=2 ./SampleScript.sh

SecondParamPassed=2 FirstParamPassed=1 ./SampleScript.sh

预命令分配的顺序无关紧要。

如果在调用脚本之前启用了-k选项,则可以将分配放在脚本之后,以模仿您的原始尝试。

$ set -k
$ ./SampleScript.sh SecondParamPassed=2 FirstParamPassed=1
First arg: 1
Second arg: 2

同样,分配顺序无关紧要。


您可以修改脚本以允许通过位置参数设置值。仅在尚未设置环境变量的情况下才使用positional参数。

: ${FirstParamPassed:=$1}
: ${SecondParamPassed:=$2}
echo "First arg: $FirstParamPassed"
echo "Second arg: $SecondParamPassed"

例如,

$ SecondParamPassed=2 ./SampleScript.sh 6 notused
First arg: 6
Second arg: 2

答案 1 :(得分:0)

只是一个简单的解析器:

#!/bin/bash
for i; do  # this is shorter form of `for i in "$@"`

        case "${i%=*}" in
        a|b|c) ;;
        *) echo "ERROR: unknown variable name '${i%=*}' passed. Only 'a', 'b' and 'c' are supported." >&2; exit 1; ;;
        esac

        declare "$i"
done
echo a="$a"
echo b="$b"
echo c="$c"

示例:

> ./1.sh a=1 b=2 c='!! @@ ## $$ '\''$(echo 123)'\''$(echo 123)'3
a=1
b=2
c=!! @@ ## $$ '$(echo 123)'$(echo 123)3

@edit
我添加了一个简单的检查,检查变量名"${i%=*}"是否为所需变量之一。另外,不需要在${i}上拆分=