grep lookbehind с якорем неожиданные результаты - PullRequest
0 голосов
/ 24 февраля 2019

Почему это закрепленное представление не работает должным образом?

$ grep -Po '^(?<=field_one: ).*' <<< "field_one: 123" # no match. non-zero exit. why?

$ grep -Po '(?<=field_one: ).*' <<< "field_one: 123"  # match, no anchor
123
$ grep -Po '(?<=^field_one: ).*' <<< "field_one: 123" # match, anchor inside lookbehind
123
$ grep -Po '^(field_one: ).*' <<< "field_one: 123"    # match, no lookbehind
field_one: 123

Версия grep: grep (GNU grep) 3.1

1 Ответ

0 голосов
/ 24 февраля 2019

Вы не можете ожидать, что ^(?<=field_one: ).* будет соответствовать любой строке, потому что ^ соответствует началу позиции строки, а затем (?<=field_one: ) в положительном взгляде требует field_one: сразу слева от текущего местоположения.Шаблон lookbehind проверяется только в начале строки.Перед началом строки нет и не может быть текста, и это своего рода регулярное выражение, которое никогда не будет совпадать ни с одной строкой.

Использовать

grep -Po '(?<=^field_one: ).*' <<< "field_one: 123"

С ^ внутри обзорной области.так как ^ будет частью проверки обхода и будет проверяться в каждой позиции, и если он найдет местоположение, которому непосредственно предшествует field_one: в начале строки, совпадение будет возвращено.

Другая альтернатива:

grep -Po '^field_one:\s*\K.*' <<< "field_one: 123"
                     ^^^^^

Здесь не используется вид сзади, шаблон ^field_one:\s* соответствует field_one: в начале строки, затем используются 0+ пробелов и \K operator отбрасывает весь найденный текст.Будет возвращен только текст, который дополнительно соответствует .*.

См. online grep demo .

...