HTML / XML делится на разметку и контент. Regex полезен только для анализа лексических тегов. Я думаю, вы могли бы вывести содержание. Это был бы хороший выбор для парсера SAX. Теги и контент могут быть доставлены в пользовательскую функцию, где можно отслеживать вложение / закрытие элементов.
Что касается простого анализа тегов, это можно сделать с помощью регулярного выражения и использовать для удаления тегов из документа.
За годы тестирования я обнаружил секрет того, как браузеры анализируют теги, как хорошо, так и плохо сформированные.
Нормальные элементы анализируются с помощью этой формы:
Ядро этих тегов использует это регулярное выражение
(?:
" [\S\s]*? "
| ' [\S\s]*? '
| [^>]?
)+
Вы заметите это [^>]?
как одно из чередований. Это будет соответствовать несбалансированным цитатам из плохо сформированных тегов.
Это также, самый корень всего зла в регулярных выражениях. То, как он используется, вызовет удар, чтобы удовлетворить его жадный, должен соответствовать количественный контейнер.
При пассивном использовании проблемы никогда не возникает. Но если вы заставляете что-либо совпадать, перемежая это с требуемой парой атрибут / значение, и не предоставляете адекватную защиту от обратного отслеживания, это неуправляемый кошмар.
Это общая форма для простых старых тегов. Обратите внимание на [\w:]
представление имени тега? На самом деле, допустимые символы, представляющие имя тега, представляют собой невероятный список символов Юникода.
<
(?:
[\w:]+
\s+
(?:
" [\S\s]*? "
| ' [\S\s]*? '
| [^>]?
)+
\s* /?
)
>
Продвигаясь дальше, мы также видим, что вы просто не можете искать определенный тег без разбора ВСЕХ тегов. Я имею в виду, что вы могли бы, но он должен был бы использовать комбинацию глаголов, таких как (* SKIP) (* FAIL), но все же все теги должны быть проанализированы.
Причина в том, что синтаксис тегов может быть скрыт внутри других тегов и т. Д.
Таким образом, для пассивного анализа всех тегов необходимо регулярное выражение, как показано ниже. Этот конкретный соответствует также невидимому контенту .
Когда новый HTML или XML или любой другой разработают новые конструкции, просто добавьте его в качестве одного из вариантов.
Примечание к веб-странице - я никогда не видел веб-страницу (или xhtml / xml), с которой
возникли проблемы. Если найдешь, дай мне знать.
Примечание по производительности - это быстро. Это самый быстрый анализатор тегов, который я когда-либо видел
(может быть, быстрее, кто знает).
У меня есть несколько конкретных версий. Это также отлично, как скребок
(если вы практический тип).
Полное необработанное регулярное выражение
<(?:(?:(?:(script|style|object|embed|applet|noframes|noscript|noembed)(?:\s+(?>"[\S\s]*?"|'[\S\s]*?'|(?:(?!/>)[^>])?)+)?\s*>)[\S\s]*?</\1\s*(?=>))|(?:/?[\w:]+\s*/?)|(?:[\w:]+\s+(?:"[\S\s]*?"|'[\S\s]*?'|[^>]?)+\s*/?)|\?[\S\s]*?\?|(?:!(?:(?:DOCTYPE[\S\s]*?)|(?:\[CDATA\[[\S\s]*?\]\])|(?:--[\S\s]*?--)|(?:ATTLIST[\S\s]*?)|(?:ENTITY[\S\s]*?)|(?:ELEMENT[\S\s]*?))))>
Отформатированный вид
<
(?:
(?:
(?:
# Invisible content; end tag req'd
( # (1 start)
script
| style
| object
| embed
| applet
| noframes
| noscript
| noembed
) # (1 end)
(?:
\s+
(?>
" [\S\s]*? "
| ' [\S\s]*? '
| (?:
(?! /> )
[^>]
)?
)+
)?
\s* >
)
[\S\s]*? </ \1 \s*
(?= > )
)
| (?: /? [\w:]+ \s* /? )
| (?:
[\w:]+
\s+
(?:
" [\S\s]*? "
| ' [\S\s]*? '
| [^>]?
)+
\s* /?
)
| \? [\S\s]*? \?
| (?:
!
(?:
(?: DOCTYPE [\S\s]*? )
| (?: \[CDATA\[ [\S\s]*? \]\] )
| (?: -- [\S\s]*? -- )
| (?: ATTLIST [\S\s]*? )
| (?: ENTITY [\S\s]*? )
| (?: ELEMENT [\S\s]*? )
)
)
)
>