为什么Unix通配符“*”不包括“。*”?

考虑只有一个文件.foo的目录。 然后rm -rf *不会删除.foo ; 只有rm -rf .*会。 这是为什么? (我想这与默认设置有关,但是devise原理是什么?当它们应该被删除时,我倾向于留下点文件。)

从Bash手册 :

当一个模式用于文件名扩展时,字符'。' 在一个文件名的开始处或紧接着一个斜杠后,必须明确地匹配,除非设置了shell选项dotglob 。 匹配文件名时,必须始终明确匹配斜线字符。 在其他情况下,“。” 字符不被特别处理。

至于理由,我只能猜测。 我想象是这样的,你不会意外地操纵你不知道的文件(记住ls不会显示.foo )。

根据Rob Pike的说法,整个概念名称以点开头的文件应该是“隐藏的” ,这是软件bug的结果 。

他特别说:

首先是一个不好的先例。 许多其他懒惰的程序员通过进行相同的简化来引入错误。 以句点开头的实际文件在计算时经常被忽略。

其次,更糟的是,创建了一个“隐藏”或“点”文件的想法。 […]

我很确定隐藏文件的概念是一个意想不到的结果。 这当然是一个错误。

抛开历史事故,将隐藏文件从通配符扩展中排除是一个很好的保守设计决策。 否则像rm *这样的命令可能会造成比用户想要的更多的伤害。

这是因为文件前缀. 通常是隐藏的,不属于正常情况下的扩张。 这意味着你不会在包含控制文件或目录的目录( 例如 .svn )中弄乱全局。 当你使用* ,你通常打算扩展到正常的文件。

这背后的设计原理是,例如.foo ,是一个隐藏的文件。 整个目录的易失性操作最终可能会造成更多的破坏。