基于此脚本:
find . -name "*.txt" | grep 'LINUX/UNIX'
Run Code Online (Sandbox Code Playgroud)
和
find . -name "*.txt" | grep 'LINUX/UNIX' | xargs cp <to a path>
Run Code Online (Sandbox Code Playgroud)
从这里 ,我可以 grep 某个字符串的文件,然后将这些文件复制到一个目录中,如果它们包含该字符串,但它们会被保存为单独的文件。如何将这些文件归类为一个连贯的文档?
示例 我的想法如下:我有一个引用档案,分布在数百个文件夹中的单独文件中,文件夹的名称是各自的主题。所以“哲学/本体论/概念/aletheia/notes.tex”将包含我所有关于aletheia等哲学概念的笔记。
它们都遵循一些命名约定(名称始终为:notes.tex),因此对它们进行 grep 很容易。我可以通过 grep 搜索它们,但我希望能够有一个脚本,它不仅可以找到它们,还可以将包含相应字符串的所有文件连接到一个大文件中。
要*.txt在当前目录或以下目录中选择名称匹配的包含特定字符串(不包含特定正则表达式的匹配项)的常规文件,并按照找到的顺序将这些文件连接在一起,您可以使用
find . -name '*.txt' -type f -exec grep -q -F 'LINUX/UNIX' {} \; -exec cat {} + >myfile
Run Code Online (Sandbox Code Playgroud)
或者
find . -name '*.txt' -type f -exec sh -c '
for pathname do
grep -q -F "LINUX/UNIX" "$pathname" && cat "$pathname"
done' sh {} + >myfile
Run Code Online (Sandbox Code Playgroud)
grep 此处使用该实用程序及其-q选项。这使得它不输出任何内容,但只要给定的模式匹配,它就会以零退出状态终止,表示“成功”。我们在上述两个命令中都使用此退出状态作为测试,以仅选择包含字符串LINUX/UNIX.
该-F选项将grep使其解释图案为字符串,而不是一个正则表达式。这可能会使命令更快一点,但也意味着您不必担心搜索字符串*this*而不必*特殊对待字符(因为它在正则表达式中很特殊)。
这两个命令都将连接的文件数据写入名为myfile. 如果该文件已经存在,它将被截断(清空),否则将被创建。我故意挑选一个输出文件名,将未由所述发现find命令,即,一个不与结束.txt。
请注意,该问题当前包含似乎过滤findwith的输出的代码,grep然后调用cpvia xargs。这不是问题的用户自己的代码,它有几个问题。一个问题是它不连接任何文件的内容,另一个问题是它将 应用于grep输出的路径名find而不是文件的内容。另请参阅为什么循环查找的输出是不好的做法?这是相关的。
要使用该代码的格式问题实际解决问题这个问题,即让find产品路径的列表,然后分开,都grep选择那些我们感兴趣,到最后cat这些:
find . -name '*.txt' -type f -print0 |
xargs -0 grep -lZ -F 'LINUX/UNIX' |
xargs -0 cat >myfile
Run Code Online (Sandbox Code Playgroud)
这将传递名称以.txtfromfind到第一个结尾的文件的路径名列表xargs作为空分隔列表。该xargs实用程序grep对这些进行调用,并grep输出包含匹配项的文件的路径名,同样以空分隔列表的形式输出。这-l使它输出匹配文件的路径名,并将-Z其转换为空分隔列表而不是换行分隔列表。
这个列表然后由在每个文件xargs上调用的 final 读取cat。连接的结果myfile像以前一样写入。
请注意,这是一种更笨拙的解决问题的方法,可能会忘记文件列表在管道阶段之间的格式,并假设运行代码的人必须使用 GNU 系统,或者至少使用 GNU 工具(即它无可救药地不可移植)。
| 归档时间: |
|
| 查看次数: |
93 次 |
| 最近记录: |