如何在嵌入通配符的“查找”搜索中排除/忽略隐藏的文件和目录?

nut*_*tty 161 command-line find

从(注意“一些文本”前后通配符)开始

find . -type f -name '*some text*'
Run Code Online (Sandbox Code Playgroud)

如何排除/忽略所有隐藏的文件和目录?

我已经在谷歌上搜索了太久,遇到了一些 -prune 和 ! (感叹号)参数,但没有合适(和简约)的例子,它刚刚工作

管道 |grep将是一个选择,我还欢迎这样的例子; 但主要是我对一个简短的单行(或几个独立的单行,说明实现相同命令行目标的不同方法)感兴趣,只是使用find.

ps:在 linux 中查找文件并排除特定目录似乎密切相关,但是 a) 尚未被接受并且 b) 是相关但不同且不同的,但是 c) 可能会提供灵感并帮助查明混淆!

编辑

find . \( ! -regex '.*/\..*' \) -type f -name "whatever",作品。正则表达式查找“​​任何东西,然后是斜杠,然后是点,然后是任何东西”(即所有隐藏的文件和文件夹,包括它们的子文件夹),以及“!” 否定正则表达式。

Fli*_*imm 179

这将打印目录的所有后代文件,跳过隐藏的文件和目录:

find . -not -path '*/\.*'
Run Code Online (Sandbox Code Playgroud)

因此,如果您要查找some text名称中包含的文件,并且想跳过隐藏的文件和目录,请运行:

find . -not -path '*/\.*' -type f -name '*some text*'
Run Code Online (Sandbox Code Playgroud)

解释:

-path选项针对整个路径字符串运行检查模式。*是通配符,/是目录分隔符,\.是点(必须转义以避免特殊含义),并且*是另一个通配符。-not意味着不要选择与此测试匹配的文件。

我认为这find不足以避免在上一个命令中递归搜索隐藏目录,因此如果您需要速度,请-prune改用,如下所示:

 find . -type d -path '*/\.*' -prune -o -not -name '.*' -type f -name '*some text*' -print
Run Code Online (Sandbox Code Playgroud)

  • @frostschutz 实际上,仔细想想,我可能错了`.` 有特殊含义。 (2认同)
  • @Flimm 是的,不需要转义“.”。据我所知,只有这些需要转义:“*”、“?”和“[]”。 (2认同)
  • 我最近发现这样的模式存在问题。如果您的搜索路径包含 (.),那么所有内容都会被过滤。例如 `find ../buildfiles` 向后移动的双点将触发 '*/.*' 模式,因为结果将是 `../buildfiles/foo, ../buildfiles/bar, ../buildfiles/等等` (2认同)

era*_*man 13

这是在 BSD、Mac 和 Linux 上也能正常工作的少数排除点文件的方法之一:

find "$PWD" -name ".*" -prune -o -print
Run Code Online (Sandbox Code Playgroud)
  • $PWD 打印当前目录的完整路径,这样路径就不会以 ./
  • -name ".*" -prune 匹配任何以点开头然后不下降的文件或目录
  • -o -print表示如果前一个表达式不匹配任何内容,则打印文件名。使用-print-print0导致所有其他表达式默认不打印。

  • “令人震惊的复杂”可能是多余的。我改写了答案以切入主题。我认为我发布的答案很难理解,如果不仔细阅读手册页就很难看到。如果您_仅_使用 GNU find,那么还有更多可能的解决方案。 (2认同)

ken*_*orb 7

你不必find为此使用。只需在 shell 中使用 globstar 即可,例如:

echo **/*foo*
Run Code Online (Sandbox Code Playgroud)

或者:

ls **/*foo*
Run Code Online (Sandbox Code Playgroud)

其中**/递归地表示任何文件夹以及名称中*foo*包含的任何文件。foo

默认情况下,使用ls将打印不包括隐藏文件和目录的文件名。

如果您没有启用通配符,请通过 执行此操作shopt -s globstar

注意:新的 globbing 选项适用于 Bash 4、zsh 和类似的 shell。


例子:

$ mkdir -vp a/b/c/d
mkdir: created directory 'a'
mkdir: created directory 'a/b'
mkdir: created directory 'a/b/c'
mkdir: created directory 'a/b/c/d'
$ touch a/b/c/d/foo a/b/c/d/bar  a/b/c/d/.foo_hidden a/b/c/d/foo_not_hidden
$ echo **/*foo*
a/b/c/d/foo  a/b/c/d/foo_not_hidden
Run Code Online (Sandbox Code Playgroud)

  • 你不需要“ls”!`回声 **/*foo*` (6认同)

小智 5

find $DIR -not -path '*/\.*' -type f \( ! -iname ".*" \)
Run Code Online (Sandbox Code Playgroud)

排除所有隐藏目录和 $DIR 下的隐藏文件


nut*_*tty 2

我最初发布的答案是对上面我原来的问题的“编辑”:

find . \( ! -regex '.*/\..*' \) -type f -name "whatever",有效。正则表达式查找“​​任何内容,然后是斜线,然后是点,然后是任何内容”(即所有隐藏文件和文件夹,包括其子文件夹),以及“!” 否定正则表达式。