我最近需要使用一个Bash for
循环来递归遍历目录中的几个文件:
for video in **/*.{mkv,mp4,webm}; do
echo "$video"
done
在花费了大量时间进行调试之后,我意识到即使模式不匹配,循环也会运行,从而导致:
file1.mkv
file2.mp4
**/*.webm # literal pattern printed when no .webm files can be found
一些详细的搜索最终发现这是known behaviour in Bash,对于它,使用shopt -s nullglob
启用shell的nullglob
选项是解决方案。
是否有理由认为这种违反直觉的行为是默认的,需要使用nullglob
显式禁用,而不是相反?或者换一种方式问,总是启用nullglob
是否有任何缺点?
1条答案
按热度按时间y3bcpkx11#
从
man 7 glob
开始:上面给出了一个简单的规则:"将通配符模式扩展到匹配路径名的列表中"是UNIX的原始定义。它允许将模式扩展到空列表中,如
其中可能不存在 *. gif文件(这不是错误)。但是,POSIX要求通配符模式在语法不正确或匹配路径名列表为空时保持不变。使用 * bash *,可以使用以下命令强制执行经典行为:
(类似的问题也会发生在其他地方。例如,旧的指令码
新脚本需要
以避免使用空参数列表调用 * rm * 时出现错误消息。)
简而言之,它是POSIX兼容所需的行为。
当然,你现在可以问POSIX指定这种行为的基本原理是什么。