Проблема реализации частичных совпадений с регулярным выражением на Android - PullRequest
3 голосов
/ 17 августа 2011

Я создаю регулярное выражение, чтобы оценить, является ли IP-адрес действительным адресом многоадресной рассылки. Эта проверка происходит в режиме реального времени, пока вы печатаете (если вы вводите недопустимый символ / символ вне диапазона, он не принимается), поэтому я не могу просто сравнить конечный результат с регулярным выражением. Проблема, с которой я сталкиваюсь, заключается в том, что она допускает двойной период после каждой группы чисел (224 .., 224.0 .., 224.0.0 .. все отображаются как действительные).

Код ниже является статическим представлением того, что происходит. Почему-то 224 .. показывается как легальная стоимость. Я протестировал это регулярное выражение онлайн (не в java'ized: ^ 2 (2 [4-9] | 3 \ d) (. (25 [0-5] | 2 [0-4] \ d | 1 \ d) \ d | [1-9] \ d | \ d)) {3} $), он отлично работает и не принимает неверный ввод, который я описываю.

Pattern p = Pattern.compile("^2(2[4-9]|3\\d)(\\.(25[0-5]|2[0-4]\\d|[0-1]?\\d?\\d)){3}$");
Matcher m = p.matcher("224..");


if (!m.matches() && !m.hitEnd()) {
    System.out.println("Invalid");
} else {
    System.out.println("Valid");
}

Кажется, что метод m.hitEnd () оценивается как истинный всякий раз, когда я ввожу 224, что для меня не имеет смысла. Если кто-то мог бы, пожалуйста, просмотреть это и удостовериться, что я не делаю никакой очевидной ошибки и, возможно, объяснить, почему hitEnd () возвращает true в этом случае, я был бы признателен. Спасибо всем.

Ответы [ 4 ]

4 голосов
/ 17 августа 2011

Проведя некоторую оценку себя (обнаружив, что это на Android), я понял, что тот же код реагирует на Dalvik иначе, чем на обычной JVM.

Код:

   Pattern p = Pattern.compile("^2(2[4-9]|3\\d)(\\.(25[0-5]|2[0-4]\\d|[0-1]?\\d?\\d)){3}$");
    Matcher m = p.matcher("224..");

    if (!m.matches() && !m.hitEnd()) {
        System.out.println("Invalid");
    } else {
        System.out.println("Valid");
    }

Этот код (хотя и немного измененный) печатает Valid на Android и Invalid на JVM.

1 голос
/ 17 августа 2011

Я не знаю, как вы проверили свое регулярное выражение, но оно не выглядит правильным в соответствии с вашим описанием.

Для вашего регулярного текста требуются все 4 раздела цифр.Нет никаких шансов, что он совпадет с 224. Только [0-1] и \ d помечены знаком вопроса и, следовательно, являются необязательными.

Таким образом, не имея дело с деталями ограничений, которые разрешены конкретными цифрами, яЯ бы посоветовал вам что-то вроде этого:

^\\d{1-3}\\.(\\d{0-3}\\.)?(\\d{0-3}\\.)?(\\d{0-3}\\.)?$

И вам не нужно использовать hitEnd (): $ в конце достаточно.И не используйте matches().Вместо этого используйте find().matches() похоже на find(), но автоматически добавляет ^ и $.

0 голосов
/ 08 октября 2011

Я сообщил ошибка 20625 в Dalvik. Тем временем вам не нужно использовать hitEnd(), достаточно суффикса $.

public void testHitEnd() {
  String text = "b";
  String pattern = "^aa$";
  Matcher matcher = Pattern.compile(pattern).matcher(text);
  assertFalse(matcher.matches());
  assertFalse(matcher.hitEnd());
}
0 голосов
/ 17 августа 2011

Я только что проверил ваш код, и m.hitEnd() оценивается как ложное для меня, и я получаю недействительное ...

Так что я не совсем уверен, в чем здесь проблема?

...