O padrão *:
corresponderá a todos até o último :
. Para parar no próximo :
, você precisa de *?:
. Por exemplo:
% grep -Poz '^:MENU1\K[\w\W]*?:' data.txt
0. public
1. admin
2. webmail
:
Você pode remover a primeira linha combinando a nova linha antes de seu \K
. Por exemplo:
% grep -Poz '^:MENU1\n\K[\w\W]*?:' data.txt
0. public
1. admin
2. webmail
:
Para comer a linha vazia e o :
, você pode combinar e descartar esse texto. Por exemplo:
% grep -Poz '^:MENU1\n\K[\w\W]*?(?=\n+:)' data.txt
0. public
1. admin
2. webmail
Em seguida, podemos simplificar sua classe de caracteres, para corresponder a qualquer coisa, exceto :
:
% grep -Poz '^:MENU1\n\K[^:]*?(?=\n+:)' data.txt
0. public
1. admin
2. webmail
E finalmente podemos reescrever a parte inicial da partida:
% grep -Poz '(?<=:MENU1\n)[^:]*?(?=\n+:)' data.txt
0. public
1. admin
2. webmail
Isso é semelhante ao que @terdon criou, mas isso cuida das linhas em branco sem outra chamada para o grep.
Este regex final faz uso de asserções look-around . A (?<=pattern)
é uma asserção look-behind
que permite corresponder o pattern
, mas não incluí-lo como parte da saída. A (?=pattern)
é uma asserção de look-ahead
e nos permite corresponder no padrão à direita sem incluí-lo na saída.