在bash脚本中转义空间

时间:2012-04-29 15:01:28

标签: linux bash

我正在尝试创建一个脚本来附加所有以.hash结尾的文件,以便由md5deep验证。名称中包含空格的文件似乎会破坏此脚本。

#!/bin/bash
XVAR=""
for f in *.hash
do
    XVAR="$XVAR -x $f "
done
md5deep -e $XVAR -r *

每当我使用名为“O S.hash”的文件运行脚本时,我会得到

O: No such file or directory

如果我将XVAR="$XVAR -x $f "更改为XVAR="$XVAR -x \'$f\' "XVAR="$XVAR -x \"$f\" "

md5deep会将输入互相渗透为“O而不是

"O: No such file or directory

脚本中的变量回显显示XVAR为-x 'O S.hash'-x "O S.hash"

shell中命令的手动输入(如md5deep -e -x "O S.hash" -r *)可以正常工作,但如果它在脚本中命令似乎中断

2 个答案:

答案 0 :(得分:3)

这不是最好的解决方案,但似乎它会起作用:

find . -name '*.hash' -printf "-x\0%p\0" | xargs -0 md5deep -r * -e

这实际上与OP想要的完全不同,所以这是Tim Pote和Jonathan Leffler建议的修改:

find . -maxdepth 1 -name '*.hash' -printf "-x\0%p\0" | xargs -0 md5deep -r * -e

答案 1 :(得分:2)

现在你知道为什么Unix系统上的人传统上避免使用带有空格的文件名(以及同样的目录名) - 必须对shell进行编程以处理这些名称是一种麻烦(对此有礼貌)。 shell设计用于没有这些名称的系统。换行也会引起很大的麻烦。

使用bash,到目前为止,您最好的解决方案是使用数组来保存元素,然后"${array[@]}"列出它们;这几乎是微不足道的:

declare -a XVAR

for file in *.hash
do
    XVAR+=("-x" "$file")
done

md5deep -e "${XVAR[@]}" -r *

利用Gordon Davisson提到的数组扩展符号。对于大量数组,请参阅bash参考手册(针对Bash 4.1)的§6.7'数组'一节信息;请参阅+=运算符的§3.4“Shell参数”部分。)

如果由于某种原因无法使用数组,则需要一个程序来转义其参数,以便shell不会扭曲事物。我有一个名为escape的程序:

XVAR=
for file in *.hash
do
    name=$(escape "$file")
    XVAR="$XVAR -x $file"
done
eval md5deep -e $XVAR -r *

使用eval,使用起来很棘手;它有效,但使用数组。