Golang 正则表达式边界和非 ASCII 字符
Go 的正则表达式边界(b)旨在匹配 ASCII 字符和非 ASCII 字符之间的边界非 ASCII 字符。但是,在某些情况下,当涉及拉丁字符时,它可能不会按预期运行。
问题
在 Go 中,b 边界仅在包围 ASCII 时才起作用人物。例如,正则表达式 b(vis)b 旨在匹配单词“vis”。然而,当单词“vis”包含拉丁字符时,例如“révisé”,b 无法将其识别为单词边界。
考虑以下 Go 代码:
<code class="go">package main import ( "fmt" "regexp" ) func main() { r, _ := regexp.Compile(`\b(vis)\b`) fmt.Println(r.MatchString("re vis e")) // Expected true fmt.Println(r.MatchString("revise")) // Expected true fmt.Println(r.MatchString("révisé")) // Expected false }</code>
运行此代码产生:
true true true
注意最后一行错误地匹配“révisé”。
解决方案
处理非以下情况ASCII 字符,您可以定义自己的自定义边界图案。一种方法是将 b 替换为以下正则表达式:
(?:\A|\s)(vis)(?:\s|\z)
此模式意味着:
此自定义边界有效地实现了 b 对 ASCII 字符所做的操作,但它也扩展到了非 ASCII 字符,例如拉丁字符。
通过将此自定义模式合并到正则表达式中,您可以获得所需的结果:
<code class="go">package main import ( "fmt" "regexp" ) func main() { r, _ := regexp.Compile(`(?:\A|\s)(vis)(?:\s|\z)`) fmt.Println(r.MatchString("vis")) // Added this case fmt.Println(r.MatchString("re vis e")) fmt.Println(r.MatchString("revise")) fmt.Println(r.MatchString("révisé")) }</code>
运行此代码现在会给出:
true true false false
如您所见,“révisé”被正确排除为匹配项。
以上是如何处理 Go 正则表达式边界中的非 ASCII 字符?的详细内容。更多信息请关注PHP中文网其他相关文章!