查找人类可读的文件

J.D*_*Doe 22 find files

我试图找到一种有效的方法来完成OverTheWire 强盗挑战第 5 级

无论如何,我有一堆文件,只有一个符合以下标准:

  • 人类可读
  • 1033 字节大小
  • 不可执行

现在,我正在使用该find命令,并且能够找到与最后两个条件匹配的文件:

find . -size 1033c ! -executable
Run Code Online (Sandbox Code Playgroud)

但是,我不知道如何排除非人类可读的文件。我为该挑战找到的解决方案使用-readabletest 参数,但我认为这行不通。-readable只查看文件的权限,而不查看其内容,而挑战描述要求提供 ASCII 文件或类似内容。

ter*_*don 24

是的,您可以使用它find来查找大小合适的不可执行文件,然后使用它file来检查 ASCII。就像是:

find . -type f -size 1033c ! -executable -exec file {} + | grep ASCII
Run Code Online (Sandbox Code Playgroud)

然而,问题并不像听起来那么简单。“人类可读”是一个非常模糊的术语。据推测,您的意思是文本。好的,但是什么样的文本?只有拉丁字符 ASCII 吗?完整的 Unicode?例如,考虑这三个文件:

$ cat file1
abcde
$ cat file2
?????
$ cat file3
abcde
?????
$ cat file4
#!/bin/sh
echo foo
Run Code Online (Sandbox Code Playgroud)

这些都是文本和人类可读的。现在,让我们看看file它们是什么:

$ file *
file1: ASCII text
file2: UTF-8 Unicode text
file3: UTF-8 Unicode text
file4: POSIX shell script, ASCII text executable
Run Code Online (Sandbox Code Playgroud)

所以,find上面的命令只会找到file1(为了这个例子,让我们假设这些文件有 1033 个字符)。您可以展开find查找字符串text

find . -type f -size 1033c ! -executable -exec file {} + | grep -w text
Run Code Online (Sandbox Code Playgroud)

使用-w,grep将只打印text被发现为独立单词的行。这应该与您想要的非常接近,但我不能保证没有其他文件类型的描述也可能包含 string text


Zet*_*eta 6

虽然-exec主要用于处理找到的文件,但它也可以用作测试。因此,我们可以将其添加到您的其他标准中:

find . \
  -size 1033c \
  -not -executable \
  -exec sh -c 'file {} | grep "text$"' \;
Run Code Online (Sandbox Code Playgroud)

请记住,grep当找不到模式时返回非零值,sh -c "COMMAND"并将返回评估结果(只要它有效)。所以这只会打印file <filename>输出以 结尾的文件text,例如“UTF-8 Unicode 文本”或“ASCII 文本”,而不是“非 ISO 扩展 ASCII 文本,带有转义序列”。

在一行中,它甚至比过去更短xargs

find . -size 1033c -not -executable -exec sh -c 'file {} | grep "text$"' \;
Run Code Online (Sandbox Code Playgroud)

请记住,您可以替换sh -c 'file {} | grep "text$"'为任何自定义命令。如果你想检查一些非常复杂的东西,提供一个 shell 脚本并使用它可能是一个更好的主意:

find . -size 1033c -not -executable -exec is_human_readable.sh {} \;
Run Code Online (Sandbox Code Playgroud)

从长远来看,这比 shell 的历史更容易维护:

#!/bin/sh
file "$@" | grep "text$" > /dev/null
Run Code Online (Sandbox Code Playgroud)


Emm*_*uel 0

你可以试试这个

find . -size 1033c ! -executable -exec file {} +
Run Code Online (Sandbox Code Playgroud)

你的挑战不允许 grep。密码文件将被报告为“ASCII 文本,带有很长的行”