Groovy 解析 GString 样式变量时的正则表达式 PatternSyntaxException

Groovy regex PatternSyntaxException when parsing GString-style variables

Groovy 这里。我得到了一个 String 和 GString-style 变量,比如:

String target = 'How now brown ${animal}. The ${role} has oddly-shaped ${bodyPart}.'

请记住,这 不是 打算用作实际的 GString!!!也就是说,我不会有 3 个字符串变量(分别为 animalrolebodyPart)Groovy 将在 运行 时解析. 相反,我希望对这些 "target" 字符串做 2 件不同的事情:

迄今为止我最好的尝试:

class TargetStringUtils {
    private static final String VARIABLE_PATTERN = "${*}"

    // Example input: 'How now brown ${animal}. The ${role} has oddly-shaped ${bodyPart}.'
    // Example desired output: 'How now brown ?. The ? has oddly-shaped ?.'
    static String replaceVarsWithQuestionMarks(String target) {
        target.replaceAll(VARIABLE_PATTERN, '?')
    }

    // Example input: 'How now brown ${animal}. The ${role} has oddly-shaped ${bodyPart}.'
    // Example desired output: [animal,role,bodyPart]    } list of strings  
    static List<String> collectVariableRefs(String target) {
        target.findAll(VARIABLE_PATTERN)
    }
}

...每当我使用 运行 任一方法时都会生成 PatternSytaxException

Exception in thread "main" java.util.regex.PatternSyntaxException: Illegal repetition near index 0
${*}
^

知道我哪里出错了吗?

问题是你没有正确转义模式,findAll 只会收集所有匹配项,而你需要 捕获 [=] 中的子模式12=].

使用

def target = 'How now brown ${animal}. The ${role} has oddly-shaped ${bodyPart}.'
println target.replaceAll(/$\{([^{}]*)\}/, '?') // => How now brown ?. The ? has oddly-shaped ?.

def lst = new ArrayList<>();
def m = target =~ /$\{([^{}]*)\}/
(0..<m.count).each { lst.add(m[it][1]) }
println lst   // => [animal, role, bodyPart]

this Groovy demo

/$\{([^{}]*)\}/ 斜杠字符串中,您可以使用单个反斜杠来转义特殊的正则表达式元字符,整个正则表达式模式看起来更清晰。

  • $ - 将匹配文字 $
  • \{ - 将匹配文字 {
  • ([^{}]*) - 第 1 组 捕获 {} 之外的任何字符,0 次或更多次
  • \} - 文字 }.