Что я делаю не так с моим регулярным выражением? - PullRequest
0 голосов
/ 04 июля 2010

Я пытаюсь захватить «Риу-Гранди-ду-Лешти» из:

...
<h1>Rio Grande Do Leste<br />
...

с использованием

var myregexp = /<h1>()<br/;

var nomeAldeiaDoAtaque = myregexp.exec(document);

что я делаю не так?

Обновление:

Осталось 2 вопроса:

1) поиск (документ) не дал результата, но его изменение на (document.body.innerHTML) сработало. Почему это?

2) Мне пришлось изменить его на: myregexp.exec (document.body.innerHTML) [1] ; чтобы получить то, что я хочу, иначе это дало бы мне некоторый результат, который включает <h1>. почему это?

3) (ответил), почему мне нужно использовать «. *»? Я думал, что это будет собирать что-нибудь между ()?

Ответы [ 3 ]

8 голосов
/ 04 июля 2010

Попробуйте /<h1>(.*?)<br/.

5 голосов
/ 04 июля 2010

В группе захвата

Группа захвата пытается захватить то, что ей соответствует .Это имеет некоторые важные последствия:

  • Группа, которая ничего не соответствует, никогда не может ничего захватывать.
  • Группа, которая соответствует только пустой строке, может захватывать только пустую строку.
  • Группе, которая повторно захватывает при попытке совпадения, остается только сохранить последний захват
    • В целом верно для большинства разновидностей, но регулярное выражение .NET является исключением (см. Связанный вопрос)

Вот простой шаблон, который содержит 2 группы захвата:

(\d+) (cats|dogs)
\___/ \_________/
  1        2

Учитывая i have 16 cats, 20 dogs, and 13 turtles, есть 2 совпадения (, как видно на rubular.com ):

  • 16 cats соответствует: группа 1 захватывает 16, группа 2 захватывает cats
  • 20 dogs соответствует: группа 1 захватывает 20группа 2 захватывает dogs

Теперь рассмотрим эту небольшую модификацию шаблона:

(\d)+ (cats|dogs)
\__/  \_________/
 1         2

Теперь группа 1 соответствует \d, то есть одной цифре.В большинстве случаев группа, которая совпадает неоднократно (в данном случае благодаря +), получает только последнее совпадение.Таким образом, в большинстве разновидностей группа 1 захватывает только последнюю найденную цифру (, как видно на rubular.com ):

  • 16 cats - это совпадение: группа1 захват 6, группа 2 захватов cats
  • 20 dogs является совпадением: группа 1 захватывает 0, группа 2 захватывает dogs

Ссылки


Жадный против неохотного против отрицательного класса символов

Теперь давайте рассмотрим проблему соответствия «все между A и ZZ».Как оказалось, эта спецификация неоднозначна: мы придумаем 3 паттерна, которые это делают, и они приведут к различным совпадениям.Какой из них «правильный», зависит от ожидания, которое неправильно передано в исходном утверждении.

Мы используем следующее в качестве ввода:

eeAiiZooAuuZZeeeZZfff

Мы используем 3 различных шаблона:

  • A(.*)ZZ дает 1 совпадение: AiiZooAuuZZeeeZZ ( как видно на ideone.com )
    • Это вариант жадный ;группа 1 соответствует и захвачена iiZooAuuZZeee
  • A(.*?)ZZ дает 1 совпадение: AiiZooAuuZZ ( как видно на ideone.com )
    • Это вариант неохотно ;группа 1 соответствует и захвачена iiZooAuu
  • A([^Z]*)ZZ дает 1 совпадение: AuuZZ ( как видно на ideone.com )
    • Это вариант класса с отрицанием ;группа 1 сопоставлена ​​и захвачена uu

Вот наглядное представление того, что они сопоставили:

         ___n
        /   \              n = negated character class
eeAiiZooAuuZZeeeZZfff      r = reluctant
  \_________/r   /         g = greedy
   \____________/g

См. связанный вопрос для более углубленного изучения.обработка различий между этими тремя методами.

Смежные вопросы


Возвращаясь к вопросу

Итак, давайте вернемся к вопросу и посмотримчто не так с шаблоном:

<h1>()<br
    \/
     1

Группа 1 соответствует пустой строке, поэтому весь шаблон в целом может соответствовать только <hr1><br, а группа 1 может соответствовать только пустой строке.

Oneможет попытаться «исправить» это разными способами.3 очевидных варианта:

  • <h1>(.*)<br;жадный
  • <h1>(.*?)<br;неохотно
  • <h1>([^<]*)<br;класс отрицанных персонажей

Вы обнаружите, что ни один из вышеперечисленных "не работает" все время; будут проблемы с некоторым HTML. Этого и следовало ожидать: регулярное выражение является «неправильным» инструментом для работы. Вы можете попытаться сделать шаблон все более и более сложным, чтобы сделать его «правильным» чаще и «неправильным» реже. Скорее всего, вы получите ужасный беспорядок, который никто не может понять и / или поддерживать, и он все равно, вероятно, не будет работать "правильно" 100% времени.

0 голосов
/ 04 июля 2010

или

^(<h1>)(.)+(<br />)

иди сюда, чтобы проверить gskinner.com

...