Синтаксический анализ регулярного выражения атрибута ASPX в c # - PullRequest
1 голос
/ 12 ноября 2011

Мне нужно найти значения атрибутов в файле ASPX с помощью регулярных выражений.

Это означает, что вам не нужно беспокоиться о искаженном HTML или каких-либо проблемах, связанных с HTML.

Мне нужнонайти значение определенного атрибута (LocText).Я хочу получить то, что внутри цитат.Любые теги ASPX, такие как <% =, <% #, <% $ и т. Д. Внутри значения, не имеют смысла для этого атрибута, поэтому рассматриваются как его часть. </p>

Регулярное выражение, с которого я начал, выглядит такthis:

LocText="([^"]+)"

Это прекрасно работает, первая группа, которая является текстом результата, получает все, кроме двойных кавычек, которые там недопустимы ("; вместо этого следует использовать)

Но файл ASPX позволяет использовать одинарные кавычки - тогда нужно применить второе регулярное выражение.

LocText='([^']+)'

Я мог бы использовать эти два регулярных выражения, но я ищу способ соединить их.

LocText=("([^"]+)"|'([^']+)')

Это также работает, но, кажется, не очень эффективно, так как создает ненужное количество групп. Я думаю, что это можно как-то сделать с помощью обратных ссылок, но я не могу заставить его работать.

LocText=(["']{1})([^\1]+)\1

Я подумал, что таким образом я сохраняю одинарную / двойную кавычку в первой группе, а затем говорю ей прочитать все, что НЕ является символом, найденным в первой группе. Это снова заключено в кавычку изпервая группа.Очевидно, я ошибаюсь, и это не работает так.

Есть ли способ соединить первые два выражения, создавая лишь минимальное количество групп с одной группой, являющейся значением атрибута, который я хочуполучить?Можно ли использовать обратную ссылку для значения одинарной / двойной кавычки, или я полностью неправильно понял их значение?

1 Ответ

2 голосов
/ 12 ноября 2011

Я бы сказал, что ваше решение с чередованием не так уж и плохо, но вы можете использовать именованные захваты , поэтому результат всегда будет найден в значении одной и той же группы:

Regex regexObj = new Regex(@"LocText=(?:""(?<attr>[^""]+)""|'(?<attr>[^']+)')");
resultString = regexObj.Match(subjectString).Groups["attr"].Value;

Объяснение:

LocText=          # Match LocText=
(?:               # Either match
 "(?<attr>[^"]+)" # "...", capture in named group <attr>
|                 # or match
 '(?<attr>[^']+)' # '...', also capture in named group <attr>
)                 # End of alternation

Другой вариант - использовать прогнозные утверждения ([^\1] не работает, поскольку вы не можете поместить обратные ссылки внутри символакласс, но вы можете использовать их в обходах):

Regex regexObj = new Regex(@"LocText=([""'])((?:(?!\1).)*)\1");
resultString = regexObj.Match(subjectString).Groups[2].Value;

Объяснение:

LocText=   # Match LocText=
(["'])     # Match and capture (group 1) " or '
(          # Match and capture (group 2)...
 (?:       # Try to match...
  (?!\1)   # (unless it's the quote character we matched before)
  .        # any character
 )*        # repeat any number of times
)          # End of capturing group 2
\1         # Match the previous quote character
...