为什么'grep -lv'输出的是包含非匹配行的文件名?
'grep -lv'列出的是包含一行或多行非匹配行的文件名。如果想要列出无匹配内容的文件名,则使用"-L"选项。 (注:例如a.txt中一部分行匹配到了,一部分行没匹配到,而b.txt中完全没有匹配上,则grep -lv将输出a.txt,而不是b.txt。因此可推测"-v"选项的操作优先级要高于"-l",即先搜索出反转行,再输出包含这些反转行的文件)
使用"|"可以实现or逻辑,如何实现AND逻辑?
grep 'paul' /etc/motd | grep 'franc,ois'将搜索出同时包含"paul"和"franc,ois"的所有行。
如何同时搜索文件和标准输入?
只需使用"-"代替标准输入的文件名即可:
正则表达式中如何表达出回文结构?(注:回文结构表示正读和反读的结果是一样的,例如12321,abcba)
可以使用反向引用来实现。例如,一个4字符的结构使用BRE来实现:
它可以匹配单词"radar"或"civic"。 Guglielmo Bondioni提出了一个正则表达式,可以搜索长达19个回文结构的字符串,其中使用了9个子表达式和9个反向引用。因为BRE或ERE最多只支持9个反向引用。
grep -E -e '^(.?)(.?)(.?)(.?)(.?)(.?)(.?)(.?)(.?).?\9\8\7\6\5\4\3\2\1$' file
为何反向引用会失效?
echo 'ba' | grep -E '(a)\1|b\1'这不会输出任何内容,因为左边的表达式"(a)\1"无法匹配,因为输入数据中没有"aa",因此右边的"\1"无法引用任何内容,意味着将不匹配任何东西。(此例中右边表达式仅在左边表达式成功匹配时才能生效。)
注:经测试,即使左边表达式能匹配上,右边表达式中引用左边的分组时也无效。例如"echo 'baaca' | grep -E '(a)\1|c\1'"可以匹配大其中的"aa",但却匹配不到"ca"。
grep如何跨行匹配?
标准的grep无法实现该功能,因为它是基于行读取的。因此,仅仅使用字符类"[:space:]"无法如你想象中那样匹配换行符。
GNU的grep有一个选项"-z",它可以处理使用"\0"结尾的行。因此,可以匹配输入数据中的换行符,但通常很可能在输出结果时,输出的是所有内容而不仅是被匹配的行,因此经常需要结合输出控制选项如"-q"来使用。例如:
如果这还不满足需求,可以将输入数据进行格式转换然后交给grep,或者使用其他工具替代grep,如"sed"、"awk"、"perl"或其他很多工具都能跨行操作。
What do 'grep', 'fgrep', and 'egrep' stand for?
The name 'grep' comes from the way line editing was done on Unix. For example, 'ed' uses the following syntax to print a list of matching lines on the screen:
'fgrep' stands for Fixed 'grep'; 'egrep' stands for Extended 'grep'.
5 Known Bugs(已知的一些bug)当"{n,m}"指定的重复次数很多时,将导致grep消耗大量内存。此外,越模糊的正则表达式消耗的时间和空间越多,也会让grep消耗大量内存。 反向引用的功能非常慢,因此可能会消耗大量时间。 (注:递归搜索时,也会消耗巨量的内存,很容易提示内存溢出错误而提前退出。)