在 bash shell 脚本中传播所有参数
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/4824590/
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
Propagate all arguments in a bash shell script
提问by Fragsworth
I am writing a very simple script that calls another script, and I need to propagate the parameters from my current script to the script I am executing.
我正在编写一个调用另一个脚本的非常简单的脚本,我需要将参数从当前脚本传播到我正在执行的脚本。
For instance, my script name is foo.sh
and calls bar.sh
例如,我的脚本名称是foo.sh
并调用bar.sh
foo.sh:
foo.sh:
bar
How can I do this without explicitly specifying each parameter?
如何在不明确指定每个参数的情况下执行此操作?
回答by Sdaz MacSkibbons
Use "$@"
instead of plain $@
if you actually wish your parameters to be passed the same.
如果您确实希望传递相同的参数,请使用"$@"
而不是普通$@
的。
Observe:
观察:
$ cat foo.sh
#!/bin/bash
baz.sh $@
$ cat bar.sh
#!/bin/bash
baz.sh "$@"
$ cat baz.sh
#!/bin/bash
echo Received:
echo Received:
echo Received:
echo Received:
$ ./foo.sh first second
Received: first
Received: second
Received:
Received:
$ ./foo.sh "one quoted arg"
Received: one
Received: quoted
Received: arg
Received:
$ ./bar.sh first second
Received: first
Received: second
Received:
Received:
$ ./bar.sh "one quoted arg"
Received: one quoted arg
Received:
Received:
Received:
回答by Chris Johnsen
For bashand other Bourne-like shells:
对于bash和其他类似 Bourne 的 shell:
java com.myserver.Program "$@"
回答by miku
Use "$@"
(works for all POSIXcompatibles).
使用"$@"
(适用于所有POSIX兼容程序)。
[...] , bash features the "$@" variable, which expands to all command-line parameters separated by spaces.
[...] ,bash 具有 "$@" 变量,它扩展到所有由空格分隔的命令行参数。
From Bash by example.
来自Bash 的例子。
回答by JDS
I realize this has been well answered but here's a comparison between "$@" $@ "$*" and $*
我意识到这已经得到了很好的回答,但这里是 "$@" $@ "$*" 和 $* 之间的比较
Contents of test script:
测试脚本内容:
# cat ./test.sh
#!/usr/bin/env bash
echo "================================="
echo "Quoted DOLLAR-AT"
for ARG in "$@"; do
echo $ARG
done
echo "================================="
echo "NOT Quoted DOLLAR-AT"
for ARG in $@; do
echo $ARG
done
echo "================================="
echo "Quoted DOLLAR-STAR"
for ARG in "$*"; do
echo $ARG
done
echo "================================="
echo "NOT Quoted DOLLAR-STAR"
for ARG in $*; do
echo $ARG
done
echo "================================="
Now, run the test script with various arguments:
现在,使用各种参数运行测试脚本:
# ./test.sh "arg with space one" "arg2" arg3
=================================
Quoted DOLLAR-AT
arg with space one
arg2
arg3
=================================
NOT Quoted DOLLAR-AT
arg
with
space
one
arg2
arg3
=================================
Quoted DOLLAR-STAR
arg with space one arg2 arg3
=================================
NOT Quoted DOLLAR-STAR
arg
with
space
one
arg2
arg3
=================================
回答by Gregory Patmore
#!/usr/bin/env bash
while [ "" != "" ]; do
echo "Received: " && shift;
done;
Just thought this may be a bit more useful when trying to test how args come into your script
只是认为这在尝试测试 args 如何进入您的脚本时可能会更有用
回答by Hampden123
My SUN Unix has a lot of limitations, even "$@" was not interpreted as desired. My workaround is ${@}. For example,
我的 SUN Unix 有很多限制,甚至“$@”也没有按预期解释。我的解决方法是 ${@}。例如,
#!/bin/ksh
find ./ -type f | xargs grep "${@}"
By the way, I had to have this particular script because my Unix also does not support grep -r
顺便说一句,我必须有这个特定的脚本,因为我的 Unix 也不支持 grep -r
回答by ColinM
If you include $@
in a quoted string with other characters the behavior is very odd when there are multiple arguments, only the first argument is included inside the quotes.
如果将$@
其他字符包含在带引号的字符串中,则当有多个参数时,行为非常奇怪,只有第一个参数包含在引号内。
Example:
例子:
#!/bin/bash
set -x
bash -c "true foo $@"
Yields:
产量:
$ bash test.sh bar baz
+ bash -c 'true foo bar' baz
But assigning to a different variable first:
但首先分配给不同的变量:
#!/bin/bash
set -x
args="$@"
bash -c "true foo $args"
Yields:
产量:
$ bash test.sh bar baz
+ args='bar baz'
+ bash -c 'true foo bar baz'
回答by kvantour
Sometimes you want to pass all your arguments, but preceded by a flag (e.g. --flag
)
有时你想传递所有参数,但前面有一个标志(例如--flag
)
$ bar --flag "" --flag "" --flag ""
You can do this in the following way:
您可以通过以下方式执行此操作:
$ bar $(printf -- ' --flag "%s"' "$@")
note:to avoid extra field splitting, you must quote %s
and $@
, and to avoid having a single string, you cannot quote the subshell of printf
.
注意:为了避免额外的字段拆分,您必须引用%s
and $@
,并且为了避免单个字符串,您不能引用printf
.
回答by user6650302
Works fine, except if you have spaces or escaped characters. I don't find the way to capture arguments in this case and send to a ssh inside of script.
工作正常,除非您有空格或转义字符。在这种情况下,我找不到捕获参数并发送到脚本内的 ssh 的方法。
This could be useful but is so ugly
这可能很有用,但太丑了
_command_opts=$( echo "$@" | awk -F\- 'BEGIN { OFS=" -" } { for (i=2;i<=NF;i++) { gsub(/^[a-z] /,"&@",$i) ; gsub(/ $/,"",$i );gsub (/$/,"@",$i) }; print # file: parent.sh
# we have some params passed to parent.sh
# which we will like to pass on to child.sh as-is
./child.sh $*
}' | tr '@' \' )
回答by Shital Shah
A lot answers here recommends $@
or $*
with and without quotes, however none seems to explain what these really do and why you should that way. So let me steal this excellent summary from this answer:
这里有很多答案推荐$@
或$*
带引号和不带引号,但是似乎没有人解释这些真正的作用以及为什么你应该这样做。所以让我从这个答案中窃取这个优秀的总结:
Notice that quotes makes all the difference and without them both have identical behavior.
请注意,引号使一切变得不同,没有它们,它们的行为都相同。
For my purpose, I needed to pass parameters from one script to another as-is and for that the best option is:
出于我的目的,我需要按原样将参数从一个脚本传递到另一个脚本,为此最好的选择是:
##代码##Notice no quotes and $@
should work as well in above situation.
注意没有引号,$@
应该在上述情况下也能正常工作。