Начиная с регулярным выражением:
^((?:(?:(?:[A-Za-z_]+)(?:[0-9]+)?)+[\.]?)+)(?:\s)?(?:\:)(?:\s)?((?:.*)+)$
^ # Anchors to the beginning to the string.
( # Opens CG1
(?: # Opens NCG
(?: # Opens NCG
(?: # Opens NCG
[A-Za-z_]+ # Character class (any of the characters within)
) # Closes NCG
(?: # Opens NCG
[0-9]+ # Character class (any of the characters within)
)? # Closes NCG
)+ # Closes NCG
[\.]? # Character class (any of the characters within)
)+ # Closes NCG
) # Closes CG1
(?: # Opens NCG
\s # Token: \s (white space)
)? # Closes NCG
(?: # Opens NCG
\: # Literal :
) # Closes NCG
(?: # Opens NCG
\s # Token: \s (white space)
)? # Closes NCG
( # Opens CG2
(?: # Opens NCG
.* # . denotes any single character, except for newline
)+ # Closes NCG
) # Closes CG2
$ # Anchors to the end to the string.
я преобразовал [0-9]
в \d
, просто для облегчения читаемости (оба совпадают то же самое). Я также удалил много не захватывающих групп, потому что они на самом деле не использовались.
^((?:(?:[A-Za-z_]+\d*)+\.?)+)\s?\:\s?((?:.*)+)$
Я также объединил \s
и. * В [\s\S]*
, но, видя, что он последовал +
знак, я удалил группу и просто сделал [\s\S]
.
^((?:(?:[A-Za-z_]+\d*)+\.?)+)\s?\:([\s\S]+)$
^
Теперь я не уверен, что +
выше карата должен делать. Мы можем удалить его и, таким образом, группу, не связанную с захватом.
^((?:[A-Za-z_]+\d*\.?)+)\s?\:([\s\S]+)$
Объяснение:
^ # Anchors to the beginning to the string.
( # Opens CG1
(?: # Opens NCG
[A-Za-z_]+ # Character class (any of the characters within)
\d* # Token: \d (digit)
\.? # Literal .
)+ # Closes NCG
) # Closes CG1
\s? # Token: \s (white space)
\: # Literal :
( # Opens CG2
[\s\S]+ # Character class (any of the characters within)
) # Closes CG2
$ # Anchors to the end to the string.
Теперь, вы можете захотеть изменить [\s\S]+
обратно .*
, если вы имеете дело с несколькими линиями. Существует несколько различных вариантов, но это вопрос, какой язык вы используете.
Честно говоря, я сделал это пошагово, но самой большой проблемой было (?:.*)+
Это сообщение двигателю match 0 or more characters 1 or more times
catastrophic backtracking (as xufox linked to in comments).
Полученное регулярное выражение и ваш оригинал также допускают переменные, которые заканчиваются на .
. Я бы использовал что-то более похожее на это, что ваше регулярное выражение действительно было не так уж далека от.
Это будет соответствовать именам, например foo.ba5r, если это приемлемо, ваше предыдущее регулярное выражение не будет.
^([A-Za-z_]\w*(?:\.[A-Za-z_]+\w*)*)\s?\:([\s\S]+)$
Объяснение:
^ # Anchors to the beginning to the string.
( # Opens CG1
[A-Za-z_] # Character class (any of the characters within)
\w* # Token: \w (a-z, A-Z, 0-9, _)
(?: # Opens NCG
\. # Literal .
[A-Za-z_] # Character class (any of the characters within)
\w* # Token: \w (a-z, A-Z, 0-9, _)
)* # Closes NCG
) # Closes CG1
\s? # Token: \s (white space)
\: # Literal :
( # Opens CG2
[\s\S]+ # Character class (any of the characters within)
) # Closes CG2
$ # Anchors to the end to the string.
Когда я попытался написать его с нуля, я пришел с '\ Ь ((?: [A-Za-Z _] [A-Za-z_0-9] * \.?) * [A-Za-z _] [A-Za-z_0-9] *): (. +) ', Который работает, но почти такой же, как ваш RegEx ... нет бесконечного цикла, который происходит с этим http://regex101.com. Но я могу подтвердить тайм-аут для вашего RegEx! – Xufox
Хорошо, так что, видимо, это работает, если эти метки '^' и '$ 'удаляются и вместо этого установлен флаг' g'. – Xufox
Я думаю, что это актуально: [Катастрофическое откат] (http://www.regular-expressions.info/catastrophic.html). – Xufox