Поскольку комментарии не могут быть вложены в HTML, регулярное выражение может сделать эту работу теоретически. Тем не менее, использование какого-либо синтаксического анализатора было бы лучшим выбором, особенно если ваш ввод не гарантированно правильно сформирован.
Вот моя попытка. Чтобы соответствовать только обычные комментарии, это будет работать. Это стало настоящим чудовищем, извините за это. Я проверил это достаточно широко, кажется, что это хорошо, но я не даю никаких гарантий.
<!--(?!\s*(?:\[if [^\]]+]|<!|>))(?:(?!-->).)*-->
Пояснение:
<!-- #01: "<!--"
(?! #02: look-ahead: a position not followed by:
\s* #03: any number of space
(?: #04: non-capturing group, any of:
\[if [^\]]+] #05: "[if ...]"
|<! #06: or "<!"
|> #07: or ">"
) #08: end non-capturing group
) #09: end look-ahead
(?: #10: non-capturing group:
(?!-->) #11: a position not followed by "-->"
. #12: eat the following char, it's part of the comment
)* #13: end non-capturing group, repeat
--> #14: "-->"
Шаги № 02 и № 11 имеют решающее значение. # 02 гарантирует, что следующие символы не обозначают условный комментарий. После этого # 11 гарантирует, что следующие символы не обозначают конец комментария, в то время как # 12 и # 13 вызывают фактическое соответствие.
Применить с флагами "global" и "dotall".
Чтобы сделать обратное (сопоставлять только условные комментарии), это будет примерно так:
<!(--)?(?=\[)(?:(?!<!\[endif\]\1>).)*<!\[endif\]\1>
Пояснение:
<! #01: "<!"
(--)? #02: two dashes, optional
(?=\[) #03: a position followed by "["
(?: #04: non-capturing group:
(?! #05: a position not followed by
<!\[endif\]\1> #06: "<![endif]>" or "<![endif]-->" (depends on #02)
) #07: end of look-ahead
. #08: eat the following char, it's part of the comment
)* #09: end of non-capturing group, repeat
<!\[endif\]\1> #10: "<![endif]>" or "<![endif]-->" (depends on #02)
Снова примените с флагами "global" и "dotall".
Шаг № 02 из-за синтаксиса «раскрытого уровня», см .: «MSDN - Об условных комментариях» .
Я не совсем уверен, где пробелы разрешены или ожидаются. При необходимости добавьте \s*
к выражению.