C0d*_*lus 11 regular-expression wildcards
我在 SuperUser 上回答了这个问题,该问题与 grepping 输出时使用的正则表达式类型有关。
我给出的答案是这样的:
tail -f log | grep "some_string.*some_string"
Run Code Online (Sandbox Code Playgroud)
然后,在对我的回答@Bob 的三个评论中写道:
.*
是贪婪的,可能会捕获比您想要的更多。.*?
通常更好。
那么这个,
这
?
是 上的修饰符*
,使其变得懒惰而不是贪婪的默认值。假设 PCRE。
我用谷歌搜索PCRE
,但无法在我的答案中得到这有什么意义?
最后这个,
我还应该指出这是正则表达式(默认情况下 grep 执行 POSIX 正则表达式),而不是 shell glob。
我只知道 Regex 是什么以及它在 grep 命令中的基本用法。所以,我无法得到这 3 条评论中的任何一条,我有这些问题:
.*?
vs. 的用法有什么区别.*
?理解评论也会有帮助,如果有人可以的话
更新:作为问题的答案Regex 与 Shell Globs 有何不同? @Kusalananda在他的评论中提供了这个链接。
注意:如果需要,请在回答参考上下文之前阅读我对这个问题的回答。
Ash*_*ora 10
假设我使用一个字符串:
can cats eat plants?
使用 greedyc.*s
将匹配整个字符串,因为它以 开头c
和结尾s
,作为一个贪心运算符,它会继续匹配直到最后出现 s。
而使用 lazyc.*?s
只会匹配,直到s
找到第一次出现的,即 string can cats
。
从上面的示例中,您可能会发现:
“贪婪”意味着匹配最长的字符串。“懒惰”意味着匹配最短的字符串。将 a 添加?
到像*
, +
, 之类的量词上?
,或者{n,m}
使它变得懒惰。
阿肖克已经指出的区别.*
和.*?
,所以我就提供一些额外的信息。
grep
(假设为 GNU 版本)支持 4 种匹配字符串的方式:
-F
选项-E
选项-P
GNU grep 中的选项grep
默认使用 BRE。
BRE 和 ERE 记录在POSIX的正则表达式一章中,PCRE 记录在其官方网站中。请注意,功能和语法可能因实现而异。
值得一提的是,BRE 和 ERE 都不支持懒惰:
多个相邻重复符号(“+”、“*”、“?”和间隔)的行为会产生未定义的结果。
因此,如果您想使用该功能,则需要改用 PCRE:
# PCRE greedy
$ grep -P -o 'c.*s' <<< 'can cats eat plants?'
can cats eat plants
# PCRE lazy
$ grep -P -o 'c.*?s' <<< 'can cats eat plants?'
can cats
Run Code Online (Sandbox Code Playgroud)
你能解释一下
.*
vs.*?
吗?
.*
用于匹配可能的“最长” 1模式。
.*?
用于匹配可能的“最短” 1模式。
根据我的经验,最想要的行为通常是第二个。
例如,假设我们有以下字符串,我们只想匹配 html 标签2,而不是它们之间的内容:
<title>My webpage title</title>
Run Code Online (Sandbox Code Playgroud)
现在比较.*
vs .*?
:
# Greedy
$ grep -P -o '<.*>' <<< '<title>My webpage title</title>'
<title>My webpage title</title>
# Lazy
$ grep -P -o '<.*?>' <<< '<title>My webpage title</title>'
<title>
</title>
Run Code Online (Sandbox Code Playgroud)
1.正如 Kusalananda 指出的那样,正则表达式上下文中“最长”和“最短”的含义有点棘手。有关更多信息,请参阅官方文档。
2.不建议用regex解析html。这只是一个用于教育目的的例子,不要在生产中使用它。
归档时间: |
|
查看次数: |
2605 次 |
最近记录: |