我正在尝试在grep
Linux 系统(Deb)中获取夺旗比赛中的旗帜。以下不会返回任何结果,我们知道flag{ }
目录中有数百个文本实例。
grep -rnw 'Downloads/' -e 'flag{' | more
为什么?我们怎样才能搜索到呢flag{
?虽然下面工作正常。
grep -rnw 'Downloads/' -e 'flag' | more
答案1
使用 时grep -w
,您要求grep
仅返回紧邻换行符(在行的开头或结尾)或非单词字符(单词字符是字母、数字或下划线)之前或之后的匹配项。
这意味着文本this is flag{a}
不会与grep -w 'flag{
' 匹配,因为文本中 后面的字符{
是单词字符。
同样,this is theflag{
也不会被 匹配grep -w 'flag{'
。
您可以丢弃该-w
选项,转而使用显式的零宽度单词边界模式(例如在开头),以便您可以匹配flag{a}
但不能匹配theflag{
。对于 GNU grep
,这可以通过使用来完成
grep -rn '\<flag{' Downloads
或者
grep -rn '\bflag{' Downloads
该\<
模式在单词开头匹配单词边界(并\>
在结尾匹配),同时\b
在开头和结尾匹配。 \<
和\>
最初继承自ex
和vi
编辑器,并且比 更可移植\b
。
GNUgrep
不支持[[:<:]]
and [[:>:]]
(其工作方式与\<
and相同\>
)在单词的开头或结尾进行匹配,但 BSDgrep
支持。 BSDgrep
不支持\b
.
答案2
Grep with -e
(表示后面跟着一个表达式)默认使用 Basic Regex。来自man grep
,在“基本正则表达式与扩展正则表达式”下(在线手册):
传统的
egrep
不支持{
元字符,而一些egrep实现\{
则支持,因此可移植脚本应该避免{
使用grep -E
模式,而应该使用[{]
来匹配文字{
。GNU grep
-E
尝试支持传统用法,假设{
它是无效间隔规范的开始,那么它并不特殊。例如,该命令grep -E '{1'
搜索两个字符的字符串{1
,而不是报告正则表达式中的语法错误。 POSIX 允许这种行为作为扩展,但可移植脚本应该避免它。
所以最便携的选择是:
grep -rnw -e 'flag[{]' 'Downloads/' | more
答案3
echo 'flag{' | grep -F 'flag{'
flag{
echo 'flag{' | grep 'flag{'
flag{
echo 'flag{' | grep -E 'flag{'
flag{