shell问题:将带有多个标志的变量发送到cmd

时间:2009-08-25 03:31:01

标签: shell

在下面,echo输出是正确的,但pgm没有正确接收标志。欣赏任何见解。

script file:
flags="-umc -v -v "
r="";for d in `ls -d /tmp/passenger*`; do r="$r -x  $d"; done
flags="$flags $r"
echo $flags
/usr/sbin/tmpwatch "$flags" -x /tmp/.X11-unix -x /tmp/.XIM-unix \
    -x /tmp/.font-unix -x /tmp/.ICE-unix -x /tmp/.Test-unix 240 /tmp

sh -x<的输出脚本

sh -x < ./tmpwatch
+ flags='-umc -v -v '
+ r=
++ ls -d /tmp/passenger.15264
+ for d in '`ls -d /tmp/passenger*`'
+ r=' -x  /tmp/passenger.15264'
+ flags='-umc -v -v   -x  /tmp/passenger.15264'
+ echo -umc -v -v -x /tmp/passenger.15264
-umc -v -v -x /tmp/passenger.15264
+ /usr/sbin/tmpwatch '-umc -v -v   -x  /tmp/passenger.15264' \
   -x /tmp/.X11-unix -x /tmp/.XIM-unix -x /tmp/.font-unix \
   -x /tmp/.ICE-unix -x /tmp/.Test-unix 240 /tmp
/usr/sbin/tmpwatch: invalid option --
tmpwatch 2.9.7 - (c) 1997-2006 Red Hat, Inc. All rights reserved.
This program may be freely redistributed under the terms of the
GNU General Public License.

我想我需要以不同的方式将$ flags输入命令......

拉​​里

2 个答案:

答案 0 :(得分:2)

如果您希望将该变量中的单词解释为该命令的单独参数,请不要在变量周围加上引号。

而不是:

/usr/sbin/tmpwatch "$flags"

使用此:

/usr/sbin/tmpwatch $flags

重新评论:

如果脚本是从cron运行的,那没有区别。该脚本由sh而不是cron解释。

shell 中的单引号阻止变量扩展。否则,变量会扩展 - 无论它们是双引号还是不引用。试试吧:

$ food=banana
$ echo $food      # echoes banana
$ echo "$food"    # echoes banana
$ echo '$food'    # echoes $food literally

引号的另一个影响,无论是单引号还是双引号,是将字符串作为单个单词传递给命令,而不是由扩展变量值中的任何空格分隔的多个单词。

答案 1 :(得分:1)

比尔说的是什么。顺便说一下,如果你正在使用bash,这就是写这个的疯狂:

#!/bin/bash    

# Store file names in an array variable. Same as (`ls -d /tmp/passenger*`),
# by the way, but the ls is unnecessary.
files=(/tmp/passenger*)

# Add each file name to $flags, adding -x in front of each.
# "/#/-x " means search for an empty string at the beginning of
# each array item, and replace it with "-x ". Effectively, that
# just prepends "-x " to each.
flags="-umc -v -v ${files[*]/#/-x }"

# No quotes around $flags, so each word is passed as a separate
# command-line argument to tmpwatch.
/usr/sbin/tmpwatch $flags -x /tmp/.X11-unix -x /tmp/.XIM-unix \
    -x /tmp/.font-unix -x /tmp/.ICE-unix -x /tmp/.Test-unix 240 /tmp

来自bash手册页:

  

${parameter/pattern/string}

     

扩展模式以生成模式,就像在路径名扩展中一样。 Parameter已展开,pattern与其值的最长匹配将替换为string。如果pattern/开头,则pattern的所有匹配都将替换为字符串。通常只替换第一场比赛。如果pattern#开头,则必须在参数展开值的开头匹配。如果模式以%开头,则它必须在参数的扩展值的末尾匹配。如果string为空,则删除pattern的匹配项,并且可省略/以下模式。如果参数为@*,则替换操作依次应用于每个位置参数,并且扩展是结果列表。如果parameter是使用@*下标的数组变量,则替换操作依次应用于数组的每个成员,并且扩展是结果列表。