如何使用grep在文件夹中查找单词?

700

在Windows中,我会搜索文件夹中包含的单词。同样地,在一个包含许多子目录和文件的目录中,我想知道是否存在特定的单词。我的grep语法搜索显示必须指定文件名,即 grep string filename

现在,我不知道文件名,我该怎么办?一位朋友建议使用grep -nr string,但我不知道这是什么意思,而且没有得到任何结果(没有响应,直到我按下Ctrl+C)。

14个回答

1105
grep -nr 'yourString*' .

末尾的点会搜索当前目录。对于每个参数的含义:

-n            Show relative line number in the file
'yourString*' String for search, followed by a wildcard character
-r            Recursively search subdirectories listed
.             Directory for search (current directory)

grep -nr 'MobileAppSer*' . (将会找到MobileAppServlet.javaMobileAppServlet.class或者MobileAppServlet.txt'MobileAppASer*.*'是另一种相同的方法。)

要查看更多参数,请使用man grep命令。


22
*在这里有什么作用?它会导致shell通配符扩展(如果有文件名与通配符模式匹配),或者grep将其视为紧随其前的字符的0个或多个重复运算符。 - usta
9
现在我们考虑 grep -nr MobileAppSer* . 的两种可能情况:1. 假设当前目录下有3个文件匹配 MobileAppSer* 通配符模式,它们的名称分别为 MobileAppServlet.java, MobileAppServlet.classMobileAppServlet.txt。那么 grep 将会被这样调用:grep -nr MobileAppServlet.class MobileAppServlet.java MobileAppServlet.txt .,这意味着在 MobileAppServlet.javaMobileAppServlet.txt 和当前目录中的其他地方搜索文本 "MobileAppServlet.class",这显然不是用户想要的结果。 - usta
7
如果当前目录中没有与 MobileAppSer* 通配符匹配的文件,那么 grep 将按原样接收参数 MobileAppSer*,因此将其视为搜索文本 "MobileAppSe" 后跟 0 或多个 "r" 出现的情况,因此它将尝试在当前目录的文件内容中查找文本 "MobileAppSe"、"MobileAppSer"、"MobileAppSerr"、"MobileAppSerrr" 等,而不是用户想要的。 - usta
5
这个正则表达式的选用是可疑的。Usta已经指出了这一点。 - kindasimple
我运行了 grep -nr 'yourString*' . 命令,并得到一些带有“二进制文件匹配”的文件。你可以添加 --text-a 来防止这种情况:grep -anr 'yourString*' . - parsley72
我认为你想要移除星号:grep -anr 'yourString' . - Micah Walter

158
grep -nr string my_directory

额外说明:这种语法grep [options] string filename在类Unix系统中被满足,因为在这些系统中,目录是一种文件类型(有一个专门指称仅被称为“文件”的实体的术语“常规文件”)。

grep -nr string从标准输入读取要搜索的内容,这就是为什么它等待你输入,并在你按下^C时停止等待(也会在按下表示文件结束的按键组合^D时停止等待)。


1
嘿,如果我想要搜索一个字符串而不考虑大小写,我必须这样做吗:grep -i -nr "我的词" . - kiki
3
@kiki:是的,这等同于使用命令 grep -inr "my word" . - usta
18
@kiki:-r 表示递归地在子目录中搜索,-n 表示每行输出的前缀是包含该行的文件的相应行号。man grep 中详细描述了这一切,以及更多内容。 - usta

72

GREP:全局正则表达式打印/解析/处理/程序。
您可以使用它来搜索当前目录。
您可以指定-R进行“递归”搜索,这意味着该程序会在所有子文件夹及其子文件夹中进行搜索,以此类推。

grep -R "your word" .

-n会显示匹配文件中的行号。
-i表示不区分大小写进行搜索(大写字母和小写字母)。


-i将执行不区分大小写的搜索(包括大写和小写字母)。

grep -inR "your regex pattern" .

4
/*. 表示当前目录下所有文件,-R 表示递归搜索(包括子目录等)。 - Stefan Steiger
谢谢。grep -inR "[0-9a-fA-F]{32}" . 可以帮助在当前目录中的文件中查找哈希值(即十六进制字符串)。https://dev59.com/V2ox5IYBdhLWcg3wbDok#25724915 - Ryan

40

还有这个选择:

find directory_name -type f -print0 | xargs -0 grep -li word

但这可能对初学者来说有点太多了。

find是一个通用的目录遍历器/列表生成器,-type f表示“查找普通文件而非目录以及命名管道等其他内容”,-print0表示“使用空字符作为分隔符,在标准输出上将它们打印出来”。find的输出被发送到 xargs -0,后者使用空字符作为记录分隔符(而不是标准换行符)以块的方式抓取其标准输入(以避免命令行长度限制),然后对每组文件应用 grep -li word。在grep中,-l表示“列出匹配的文件”,-i表示“不区分大小写”;通常可以组合单字符选项,因此您经常会看到 -li-l -i更常见。

如果不使用-print0-0,则会遇到包含空格的文件名问题,因此使用它们是一种好习惯。


我可以排除某些目录吗? @muistooshort - Fero
1
@Ferologics,应该有的,可以从命令行中检查man find以查看您的find支持哪些选项。 - mu is too short
但对于初学者来说,这可能有点太多了。-- 长度不会因为你的个人经验而改变! - Lee Goddard

29
grep -nr search_string search_dir

将对search_string进行递归搜索(包括目录及其所有子目录)。(正如usta所正确回答的那样)。

你之前没有得到任何答案的原因是,你朋友建议的方法是不正确的:

grep -nr string

是因为没有指定目录。如果你在想要搜索的目录中,你需要执行以下操作:

grep -nr string .

包含 "." 字符很重要,因为它告诉 grep 在当前目录下搜索。


嗨,如果我需要在两个单词之间进行搜索,该怎么办?这些单词应该用引号指定吗?即 grep -nr "my word" . - kiki

13

为什么不进行递归搜索以查找子目录中的所有实例:

grep -r 'text' *

这个非常有效。


1
无需引用无特殊字符(如空格)的搜索字符串。 - Scott Stensland

10

与@eLRuLL发布的答案类似,指定一个尊重单词边界的搜索更简单的方法是使用-w选项:

grep -wnr "yourString" .

在 cmd 提示符或 Windows 终端中,grep 术语未被识别。 - kouty
1
@kouty grep是Unix命令。https://www.itechtics.com/using-findstr-windows/ - Hugo M. Zuleta

5

我喜欢使用的另一种选项:

find folder_name -type f -exec grep your_text  {} \;

-type f 仅返回文件而不是文件夹。

-exec 和 {} 在搜索中找到的文件上运行grep(确切的语法为“-exec command {}”)。


5
  1. grep -r "yourstring" * 将在任何文件和文件夹中查找 "yourstring"

现在,如果您想同时查找两个不同的字符串,您可以始终使用选项E并添加搜索词。例如,在断点之后:

  1. grep -rE "yourstring|yourotherstring|$" * 将搜索匹配 yourstringyourotherstring 的列表位置

5
grep -R "string" /directory/

-R 跟随符号链接,而 -r 不会。

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接