如何在bash脚本中省略某些输入变量(如$ 1和$ 2)的同时使用$ *?


15

例如,

elif [[ $append = $1 ]]
then
  touch ~/directory/"$2".txt
  echo "$variable_in_question" >> ~/directory/"$2".txt

创建一个包含所有后续输入的文本文件"$2",或者追加一个现有所有输入后的文本文件,用"$2"什么代替"$variable_in_question"第4行?

我基本想要"$*",但是省略"$1""$2"

Answers:


32

您可以使用bash参数扩展来指定范围,这也适用于位置参数。对于$3…… $n它将是:

"${@:3}" # expands to "$3" "$4" "$5" …
"${*:3}" # expands to "$3 $4 $5 …"

请注意两者,$@$*忽略第一个参数$0。如果您想在自己的情况下使用哪一个:很有可能需要加引号$@。不要使用$*,除非你明确地想要的参数进行单独报价。

您可以尝试如下操作:

$ bash -c 'echo "${@:3}"' 0 1 2 3 4 5 6
3 4 5 6
$ echo 'echo "${@:3}"' >script_file
$ bash script_file 0 1 2 3 4 5 6
2 3 4 5 6

请注意,在第一个示例$0中,第一个参数已填充,0而在脚本中使用时,$0则用脚本的名称填充,如第二个示例所示。脚本的名称bash当然第一个参数,只是通常不会这样认为–将脚本制成可执行文件并称为“直接”也是如此。因此,在第一个示例中,我们有$0= 0$1= 1等。在第二个示例中,我们是$0= script_file$1= 0$2= 1等。${@:3}选择以开头的每个参数$3

可能范围的一些其他示例:

 # two arguments starting with the third
$ bash -c 'echo "${@:3:2}"' 0 1 2 3 4 5 6
3 4
 # every argument starting with the second to last one
 # a negative value needs either a preceding space or parentheses
$ bash -c 'echo "${@: -2}"' 0 1 2 3 4 5 6
5 6
 # two arguments starting with the fifth to last one
$ bash -c 'echo "${@:(-5):2}"' 0 1 2 3 4 5 6
2 3

进一步阅读:


27

您可以使用shift内置的:

$ help shift
shift: shift [n]
    Shift positional parameters.

    Rename the positional parameters $N+1,$N+2 ... to $1,$2 ...  If N is
    not given, it is assumed to be 1.

    Exit Status:
    Returns success unless N is negative or greater than $#.

例如 给定

$ cat argtest.bash 
#!/bin/bash

shift 2

echo "$*"

然后

$ ./argtest.bash foo bar baz bam boo
baz bam boo

3
@Oreoplasm我认为这是值得一提的是,shift办法将使其无法访问$1$2你移位后他们。在脚本中,您可以$2与一起使用$variable_in_question,或者需要更改它或使用“参数扩展”方法。
甜点

6
shift是好当的第一个或多个ARG游戏特殊的,它是有道理的挑出来为独立的变量(foo="$1"; bar="$2";if [[ something with $1 ]];then blah blah; shift,但@甜点与非破坏性的办法答案是在其他情况下很好的时候,你还是想完整列表后,或者当您使用奇特的语法选择有限范围的args(而不是无穷大)时,如果$@没有那么多元素,而没有在命令中引入空args的话
Peter Cordes 18-3-4

13

通常,您可以将位置参数复制到数组中,删除数组的任意索引,然后使用数组将其扩展为所需的那些索引,而不会丢失原始参数。

例如,如果我想要除第一个,第四个和第五个之外的所有参数:

args=( "$@" )
unset args[0] args[3] args[4]
echo "${args[@]}"

在副本中,索引$0不是的一部分,因此移位了1 $@


1
当然,可以将其组合起来,例如echo "${args[@]:2}",倒数第二个参数。
甜点
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.