正则表达式匹配
我想写一个正则表达式来匹配之间的任何东西
()
(())
(()())
((()))
()()()
等等
所有这些答案声称你不能使用模式匹配一个字符串与平衡嵌套parens是相当错误的。 假设现代编程语言所匹配的模式在病理学教科书意义上被限制为“常规语言”是不现实的。 只要你允许反向引用,他们就不会。 这使得真实世界的模式可以比教科书版本更多地匹配,使它们更加实用。
匹配平衡零件的最简单模式是((?:[^()]*+|(?0))*)
。 但是你不应该写那个,因为它太紧凑,不容易阅读。 您应该始终使用/x
模式编写它以允许空格和注释。 所以这样写:
m{
( # literal open paren
(?: # begin alternation group
[^()]*+ # match nonparens possessively
| # or else
(?0) # recursively match entire pattern
)* # repeat alternation group
) # literal close paren
}x
为命名你的抽象也有很多要说的,并且将它们的定义和它的排序从它们的执行中分离出来。 这导致了这样的事情:
my $nested_paren_rx = qr{
(?&nested_parens)
(?(DEFINE)
(?<open> ( )
(?<close> ) )
(?<nonparens> [^()] )
(?<nested_parens>
(?&open)
(?:
(?&nonparens) *+
|
(?&nested_parens)
) *
(?&close)
)
)
}x;
第二种形式现在可以包含在更大的模式中。
永远不要让任何人告诉你不能使用模式来匹配递归定义的东西。 正如我刚才所展示的,你当然可以。
当你在它的时候,确保永远不要写行噪声模式。 你不必,也不应该。 禁止使用禁止空白,注释,子例程或字母数字标识符的编程语言。 所以在你的模式中使用所有这些东西。
当然,这对于为这类工作选择正确的语言确实有帮助。 ☺
如果您遇到正则表达式语法不支持递归匹配的语言,我会给您一些简单的Javascript实现,您可以根据自己的选择使用自己的语言:
function testBraces(s) {
for (var i=0, j=0; i<s.length && j>=0; i++)
switch(s.charAt(i)) {
case '(': { j++ ; break; }
case ')': { j-- ; break; }
}
return j == 0;
}
在这里你可以玩它:http://jsfiddle.net/BFsn2/
正则表达式无法有效处理这种嵌套结构。 你需要的是语法和语法分析器。 在你的情况下,语法很简单。 如果你正在使用python try pyparsing或者funcparserlib。
通过pyparsing,您可以执行以下操作:
from pyparsing import nestedExpr
nestedExpr().parseString( "(some (string you) (want) (to) test)" ).asList()
这将返回一个包含嵌套字符串解析组件的列表。 nestedExpr的默认分隔符是括号,因此您不必额外做任何事情。 如果你想使用funcpasrerlib你可以尝试以下
from funcparserlib.parser import forward_decl, many, a
bracketed = forward_decl()
bracketed.define(a('(') + many(bracketed) + a(')'))
之后你可以打电话
bracketed.parse( "( (some) ((test) (string) (you) (want)) (to test))" )
它将返回元组中的解析元素。
链接地址: http://www.djcxy.com/p/29865.html上一篇: Regular expression matching
下一篇: How to use Regular Expressions (Regex) in Microsoft Excel both in