如何找到与java中的输入匹配的正则表达式模式的一部分?

时间:2013-07-05 03:12:24

标签: java regex

我有模式“abc | de。| ghi”和“def”的输入。如何找到与“def”匹配的模式部分?所以,在这个例子中,我想要的结果是“de。”。不是“def”,这是我能够使用组和开始/结束方法获得的全部。

在代码中:

Pattern p = Pattern.compile("abc|de.|ghi");
Matcher m = p.matcher("def");
if(matcher.find()) {
    // Here I want to get the String "de." somehow
}

3 个答案:

答案 0 :(得分:3)

它有点四处,但你可以用捕获组做你想做的事情:

Pattern p = Pattern.compile("(abc)|(de.)|(ghi)");
Matcher m = p.matcher("def");
if(m.find()) {
    if (m.group(1) != null)
        System.out.println("Matched \"abc\"");
    if (m.group(2) != null)
        System.out.println("Matched \"de.\"");
    if (m.group(3) != null)
        System.out.println("Matched \"ghi\"");
}

答案 1 :(得分:1)

所以,你想要返回与input ...匹配的正则表达式。猜猜在Pattern或Matcher类中没有这样的方法来返回由或分开的精确模式或

所以,你可以这样做

public static String getMatchedRegexPattern(String inputRegex,String input) throws Exception
{
    if(Pattern.compile("(?<!\\\\)([\\(\\)\\[\\]])").matcher(inputRegex).find())throw new Exception("Groups,brackets not supported");
    for(String regex:inputRegex.split("(?<!\\\\)\\|"))//split only if | is not escaped
    {
    if(Pattern.compile(regex).matcher(input).matches())
        return regex;
    }
    return "";
}

您可以将其称为

getMatchedRegexPattern("abc|de.|ghi","def");

答案 2 :(得分:1)

在标准库中使用Pattern进行此操作并不容易。

source code for Pattern使用递归下降解析器来创建Node个对象的树,每个对象都支持match()方法。例如,要评估|,行4107处有一个Branch子类,用于存储可能的备选列表。其match()方法尝试每个备选方案,如果任何一个备选方案匹配且后继节点匹配,则返回true。否则返回false

通过在解析树中插入特殊的GroupHeadGroupTail节点来保存组,这会将每个组的开始和结束位置保存到Pattern类的私有变量中。

要找出模式的哪些部分导致匹配,节点对象需要知道导致它们被创建的模式部分。解析器根本不会将该信息存储在它创建的节点中。原始模式存储在temp数组中,递归下降解析器在解析时将cursor索引保留在temp数组中。从{15}行开始定义的peek()accept()之类的解析器辅助方法只需根据需要增加cursor。创建节点时,cursor的值不会存储在任何位置。但是,该值对于重建模式的哪些部分对应于匹配是必要的。

为什么Pattern不能保存这些信息是可以理解的:它会减慢所有正则表达式的评估速度,但几乎不会使用其他功能。

一种可能性是创建Pattern的修改版本,该版本执行适当的簿记以将匹配回溯到它们来自的模式部分。为了存储每个节点对应的模式的哪一部分,您可以使Node()构造函数存储cursor字段的副本。但是,要使用该数据查找模式的哪些部分匹配,您需要更新每个Node子类的match()方法,以根据Node的每个子类的语义来存储范围。 ...

祝你好运!