regex - golang 中嵌套组的正则表达式问题

标签 regex go re2

考虑以下玩具示例。我想在 Go 中用正则表达式匹配名称,其中名称是字母序列 a,由单个 # 分隔,所以 a#a#aaa 有效,但 a#a##a 无效。我可以通过以下两种方式对正则表达式进行编码:

r1 := regexp.MustCompile(`^a+(#a+)*$`)
r2 := regexp.MustCompile(`^(a+#)*a+$`)

这两个都有效。现在考虑匹配由单斜杠分隔的一系列名称的更复杂的任务。如上所述,我可以用两种方式编写代码:

^N+(/N+)*$
^(N+/)*N+$

其中 N 是去掉了 ^ 和 $ 的名称的正则表达式。由于 N 有两种情况,所以现在我可以有 4 个正则表达式:

    ^a+(#a+)*(/a+(#a+)*)*$
    ^(a+#)*a+(/a+(#a+)*)*$
    ^((a+#)*a+/)*a+(#a+)*$
    ^((a+#)*a+/)*(a+#)*a+$

问题是为什么在匹配字符串 "aa#a#a/a#a/a" 时第一个失败,而其余 3 个情况按预期工作? IE。是什么导致第一个正则表达式不匹配?完整code是:

package main

import (
    "fmt"
    "regexp"
)

func main() {
    str := "aa#a#a/a#a/a"
    regs := []string {
        `^a+(#a+)*(/a+(#a+)*)*$`,
        `^(a+#)*a+(/a+(#a+)*)*$`,
        `^((a+#)*a+/)*a+(#a+)*$`,
        `^((a+#)*a+/)*(a+#)*a+$`,
    }    
    for _, r := range(regs) {
        fmt.Println(regexp.MustCompile(r).MatchString(str))
    } 
}

令人惊讶的是它打印出 false true true true

最佳答案

这一定是golang正则表达式引擎的一个bug。一个更简单的测试用例是 ^a(/a+(#a+)*)*$ 无法匹配 a/a#a^(a)(/a+(#a+)*)*$ 有效,参见 http://play.golang.org/p/CDKxVeXW98 .

我提交了 https://github.com/golang/go/issues/11905

关于regex - golang 中嵌套组的正则表达式问题,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/31663430/

相关文章:

regex - 命名捕获组中的顺序

c++ - 在文件中搜索一个单词并在 C 中替换它?

go - Go 在 C++ 中相当于 assert() 是什么?

python - 为什么 re2 结果与 Python 中的 re 模块不同?

正则表达式匹配字符串中的 2 个或多个数字

正则表达式将文件中的空格减少 1

javascript - 如何使用正则表达式从字符串中去除 [a-z]/[a-z]/?

session - 在golang中将数组结构设置为 session

MongoDB Atlas Golang mgo包 "No reachable servers"错误

regex - 如何删除括号之间的字符串