Trzy różne sed
polecenia:
sed '$!N;s/"[^"]*"\n<[^>]*>/other characters /;P;D'
sed -e :n -e '$!N;s/"[^"]*"\n<[^>]*>/other characters /;tn'
sed -e :n -e '$!N;/"$/{$!bn' -e '};s/"[^"]*"\n<[^>]*>/other characters /g'
Wszystkie trzy opierają się na podstawowym s///
poleceniu dotyczącym upodstytucji:
s/"[^"]*"\n<[^>]*>/other characters /
Wszyscy oni również starają się zachować ostrożność w obsłudze ostatniego wiersza, ponieważ sed
zwykle różnią się wydajnością w przypadku krawędzi. To jest znaczenie $!
adresu odpowiadającego każdej linii, która !
nie jest $
ostatnia.
Wszyscy oni również używają N
polecenia ext, aby dołączyć następny wiersz wejściowy do przestrzeni wzorów po \n
znaku ewline. Każdy, kto sed
przez jakiś czas \n
grał, nauczy się polegać na postaci ewline - ponieważ jedynym sposobem na zdobycie takiego jest wyraźne umieszczenie go tam.
Wszystkie trzy podejmują próbę odczytania jak najmniejszej ilości danych wejściowych przed podjęciem działania - sed
działają tak szybko, jak to możliwe i nie muszą czytać całego pliku wejściowego przed wykonaniem tej czynności.
Chociaż robią wszystko N
, wszystkie trzy różnią się metodami rekurencji.
Pierwsze polecenie
Pierwsze polecenie wykorzystuje bardzo prostą N;P;D
pętlę. Te trzy polecenia są wbudowane w dowolny kompatybilny z POSIX sed
i ładnie się uzupełniają.
N
- jak już wspomniano, dołącza N
linię wejściową ext do przestrzeni wzorów po wstawionym \n
ograniczniku ewline.
P
- jak p
; to P
rints wzorzec-przestrzeń - ale tylko do pierwszego występującego \n
charakteru ewline. I tak, biorąc pod uwagę następujące dane wejściowe / polecenia:
printf %s\\n one two | sed '$!N;P;d'
sed
P
rints tylko jeden . Jednak z ...
D
- jak d
; to D
eletes wzorzec-przestrzeń i zaczyna kolejną linię cyklu. W przeciwieństwie do d
, D
usuwa tylko do pierwszego występującego \n
ewline w przestrzeni wzorca. Jeśli po \n
znaku ewline w przestrzeni wzorcowej znajduje się więcej przestrzeni , sed
rozpoczyna się następny cykl linii od tego, co pozostało. Jeżeli d
w poprzednim przykładzie zostały zastąpione z D
, na przykład, sed
by P
rukuj zarówno jeden i dwa .
To polecenie jest powtarzane tylko dla wierszy, które nie pasują do s///
instrukcji ubstitution. Ponieważ s///
ubstitution usuwa \n
dodaną ewline N
, nigdy nie pozostaje nic po sed
D
usunięciu przestrzeni wzorców.
Testy można wykonać w celu zastosowania P
i / lub D
wybiórczo, ale są też inne polecenia, które lepiej pasują do tej strategii. Ponieważ rekurencji jest realizowany obsłużyć kolejne linie, które pasują tylko część reguły zastępczej, kolejne sekwencje linii pasujących oba końce na s///
ubstitution nie działają dobrze .:
Biorąc pod uwagę ten wkład:
first "line"
<second>"line"
<second>"line"
<second>line and so on
... drukuje ...
first other characters "line"
<second>other characters line and so on
Poradzi sobie jednak
first "line"
second "line"
<second>line
...w porządku.
Drugie polecenie
To polecenie jest bardzo podobne do trzeciego. Obaj stosują etykietę :b
ranch / t
est (jak pokazano również w odpowiedzi Joesepha R. tutaj ) i powracają do niej pod pewnymi warunkami.
-e :n -e
- przenośne sed
skrypty ograniczają :
definicję etykiety za pomocą \n
ewline lub nowej wbudowanej -e
instrukcji xecution .
:n
- definiuje etykietę o nazwie n
. To może być zwrócone w dowolnym momencie albo bn
albo tn
.
tn
- t
komenda est powraca do określonej etykiety (lub, jeśli nie została podana, kończy działanie skryptu dla bieżącego cyklu linii), jeśli jakakolwiek s///
ubstitution od czasu zdefiniowania etykiety lub ostatniego wywołania t
ests zakończyła się powodzeniem.
W tym poleceniu następuje rekurencja dla pasujących linii. Jeśli z sed
powodzeniem zastąpi wzorzec innymi znakami , sed
powraca do :n
etykiety i próbuje ponownie. Jeśli s///
nie zostanie wykonana sed
umstitution, automatycznie drukuje się przestrzeń wzorcowa i rozpoczyna się następny cykl linii.
Zwykle lepiej radzi sobie z kolejnymi sekwencjami. Tam, gdzie ostatni zawiódł, wyświetla się:
first other characters other characters other characters line and so on
Trzecie polecenie
Jak wspomniano, logika tutaj jest bardzo podobna do ostatniej, ale test jest bardziej wyraźny.
/"$/bn
- to jest sed
test. Ponieważ b
polecenie ranch jest funkcją tego adresu, sed
będzie b
rancho tylko :n
po \n
dodaniu ewline, a przestrzeń wzorców nadal kończy się "
podwójnym cudzysłowem.
Jest tak mało zrobione pomiędzy N
i b
jak to możliwe - w ten sposób sed
można bardzo szybko zebrać dokładnie tyle danych, ile jest to konieczne, aby upewnić się, że poniższy wiersz nie pasuje do twojej reguły. W s///
różni się tutaj tym, że zatrudnia ubstitution g
skroniowe flagi - i tak to zrobi wszelkie niezbędne zamienniki naraz. Biorąc pod uwagę identyczne dane wejściowe, polecenie wypisuje identycznie do ostatniego.
\n
oświadczenie ewline zrobić dlatego pytam. ludzie rzadko pytają, czy mogą zrobićs//\n/
tak, jak ty z GNUsed
, chociaż większość innychsed
odrzuca tę ucieczkę po prawej stronie. mimo to funkcja\n
ucieczki będzie działać po lewej stronie w dowolnym POSIXsed
- ie i można je przenośnie tłumaczyć tak,y/c/\n/
jakby miało to ten sam efekt, cos/c/\n/g
nie zawsze jest tak przydatne.