【问题标题】:How do I do a case insensitive regular expression in Go?如何在 Go 中执行不区分大小写的正则表达式?
【发布时间】:2023-03-28 09:35:01
【问题描述】:

当然,我可以编写正则表达式来处理这两种情况,例如regexp.Compile("[a-zA-Z]"),但我的正则表达式是由用户给出的字符串构造的:

reg, err := regexp.Compile(strings.Replace(s.Name, " ", "[ \\._-]", -1))

其中s.Name 是名称。这可能类似于“西北偏北”。现在,对我来说最明显的解决方案是遍历s.Name 的每个字符并为每个字母写下'[nN]':

for i := 0; i < len(s.Name); i++ {
  if s.Name[i] == " " {
    fmt.Fprintf(str, "%s[ \\._-]", str);
  } else {
    fmt.Fprintf(str, "%s[%s%s]", str, strings.ToLower(s.Name[i]), strings.ToUpper(s.Name[i]))
  }
}

但我觉得这是一个相当不优雅的解决方案。速度不是问题,但我需要知道是否有其他方法。

【问题讨论】:

    标签: regex go


    【解决方案1】:

    您可以将不区分大小写的标志设置为正则表达式中的第一项。

    您可以通过将"(?i)" 添加到正则表达式的开头来做到这一点。

    reg, err := regexp.Compile("(?i)"+strings.Replace(s.Name, " ", "[ \\._-]", -1))
    

    对于固定的正则表达式,它看起来像这样。

    r := regexp.MustCompile(`(?i)CaSe`)
    

    有关标志的更多信息,请搜索 regexp/syntax 包文档 (或syntax documentation) 对于“标志”一词。

    【讨论】:

    • 但是我发现这太慢了,当有很多数据时。因为在 regexp.Match 中调用了 unicode.SimpleFold,所以我建议将字母改为大写,然后使用 regexp 进行匹配。这就是速度。以下是时间数据: ``` #By (?i) regexp to ignore case XCMP/bin/otacmp -o BSP_2.2.0.html -f BSP/frameworks -f Code/frameworks 1271.94s user 7.32s system 97% cpu 21:54.95 总计 #By toUpper 并匹配 XCMP/bin/otacmp -o BSP_2.2.0.html -f BSP/frameworks -f 代码/框架 263.87s 用户 8.99s 系统 110% cpu 4:06.44 总计 ```
    • 看起来不区分大小写的正则表达式的性能缓慢是一个已知错误,已在接下来的几个月中修复:github.com/golang/go/issues/13288
    【解决方案2】:

    您可以在模式的开头添加(?i) 以使其不区分大小写。

    Reference

    【讨论】:

      【解决方案3】:

      我对Go不太熟悉,但是根据这个例子:http://play.golang.org/p/WgpNhwWWuW

      您需要在您的正则表达式语句前加上(?i)

      【讨论】:

        【解决方案4】:

        使用i 标志。引用提示documentation

        分组:

        (re)           numbered capturing group
        (?P<name>re)   named & numbered capturing group
        (?:re)         non-capturing group
        (?flags)       set flags within current group; non-capturing
        (?flags:re)    set flags during re; non-capturing
        

        标志语法是 xyz (set) 或 -xyz (clear) 或 xy-z (set xy, clear z)。标志是:

        i              case-insensitive (default false)
        m              multi-line mode: ^ and $ match begin/end line in addition to begin/end text (default false)
        s              let . match \n (default false)
        U              ungreedy: swap meaning of x* and x*?, x+ and x+?, etc (default false)
        

        【讨论】:

        • 我应该将这些 i、m、s 和 U 放在代码的什么位置?
        • 这个答案和文档一样没有帮助。值得庆幸的是,下面有一个工作示例。
        猜你喜欢
        • 1970-01-01
        • 2011-04-22
        • 2022-01-09
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多