Я обнаружил некоторое неожиданное поведение в реализации Java regex. При использовании java.util.regex.Pattern
и java.util.regex.Matcher
следующее регулярное выражение не соответствует корректно на входе "Merlot"
при использовании метода Matcher find()
:
((?:White )?Zinfandel|Merlot)
Если я изменяю порядок выражений внутри самой внешней сопоставимой группы, метод Matcher find()
соответствует.
(Merlot|(?:White )?Zinfandel)
Вот несколько тестовых кодов, которые иллюстрируют проблему.
RegexTest.java
import java.util.regex.*;
public class RegexTest {
public static void main(String[] args) {
Pattern pattern1 = Pattern.compile("((?:White )?Zinfandel|Merlot)");
Matcher matcher1 = pattern1.matcher("Merlot");
// prints "No Match :("
if (matcher1.find()) {
System.out.println(matcher1.group(0));
} else {
System.out.println("No match :(");
}
Pattern pattern2 = Pattern.compile("(Merlot|(?:White )?Zinfandel)");
Matcher matcher2 = pattern2.matcher("Merlot");
// prints "Merlot"
if (matcher2.find()) {
System.out.println(matcher2.group(0));
} else {
System.out.println("No match :(");
}
}
}
Ожидаемый результат:
Merlot
Merlot
Но фактический вывод:
No Match :(
Merlot
Я проверил, что это неожиданное поведение существует в Java версии 1.7.0_11 на Ubuntu linux, а также Java версии 1.6.0_37 на OSX 10.8.2. Вчера я сообщил об этом поведении в качестве ошибки Oracle и получил автоматическое письмо, в котором сообщается, что мой отчет об ошибке получен и имеет внутренний идентификатор проверки 2441589. Я могу" t найти отчет об ошибке, когда я ищу этот идентификатор в своей базе данных ошибок. (Вы слышите сверчков?)
Я обнаружил ошибку в Java, предположительно тщательно протестированную и использующую реализацию регулярного выражения (трудно поверить в 2013), или я делаю что-то неправильно?