我有一个看起来像这样的shell脚本:
foreach dir (i686.* amd64.*)
# commands
end
此脚本的问题是,如果没有与这些名称匹配的目录,则会出现以下错误:
"foreach: No match."
防止此错误的优雅方法是什么?
答案 0 :(得分:3)
以下是处理此问题的两种方法。
设置shell的nonomatch
变量。如果它与任何文件都不匹配,这告诉tcsh保持模式不变。因此:
% set nonomatch=1
% echo i686.* amd64.*
i686.* amd64.*
然后,您需要让命令处理不匹配模式的情况。
传递一个总是匹配的额外模式。例如:
% echo i686.* amd64.* /dev/nul[l]
/dev/null
然后,您需要使命令忽略始终匹配模式匹配的文件。这可能比#1更容易。
答案 1 :(得分:3)
您可以使用grep
或egrep
而不是文件匹配模式:
foreach dir ( `ls | egrep '^(i686\|amd64)\.'` )
# commands
end
如果没有文件匹配,ls | egrep ...
命令就不会产生任何输出,并且循环体不会执行。
如果名称为dir
,您可能需要添加一个测试,任何匹配的文件名实际上都是一个目录。
一个更丑陋的选择是临时创建匹配文件:
tmp=i686.$$
mkdir $tmp
foreach dir (i686.* amd64.*)
if ($dir != $tmp) then
# commands
endif
end
rm $tmp
我不一定推荐这个。
如果您需要担心包含有趣字符的目录名称,您可能需要使用:q
后缀或添加双引号。