Jak sprawdzić, czy ciąg zawiera podciąg w Bash

How Check If String Contains Substring Bash



Pytanie brzmi, jak sprawdzić, czy ciąg zawiera podciąg w Bash. Odpowiedź brzmi: użyj dopasowywania wzorców. Rodzi to kolejne pytanie, które brzmi: co to jest dopasowanie wzorców? Cóż, fraza w zdaniu ma pewne cechy. Dlatego różni się od innych zwrotów w tym samym zdaniu lub w innych zdaniach. Charakterystyki można zakodować jako wzór. W ten sposób można zidentyfikować konkretną frazę w ciągu. W tym artykule wyjaśniono, jak zidentyfikować określony podciąg w większym ciągu, zastąpić dopasowany podciąg innym podciągiem i zlokalizować dowolny podciąg w większym ciągu według indeksu. Jednak zanim zagłębimy się w wyjaśnienia, trzeba przypomnieć sobie różne sposoby tworzenia struny w Bashu.

Ciąg przez ucieczkę od spacji

Ciąg można skonstruować, zastępując każdą spację sekwencją ucieczki spacji, „”; jak w:







myVar=Turystykaw Egipt jest jednym z kraju 's wiodących gospodarczych branż.
wyrzucił $myVar

Dane wyjściowe to:



Turystyka w Egipcie jest jedną z wiodących gałęzi gospodarki kraju.



Uwaga: apostrof również używał sekwencji ucieczki przestrzeni.





Ciąg według pojedynczych cytatów

Czy programista ma czas na ucieczkę od wszystkich spacji w ciągu? Nie. Dlatego użycie dwóch pojedynczych cudzysłowów do oddzielenia ciągu jest lepsze; Jak na przykład:

myVar=„Turystyka w Egipcie jest jednym z krajów” 'wiodących gałęzi gospodarki.

Łańcuch w pojedynczym cudzysłowie nie pozwala na interpretację (zastępowanie jej efektem) jakiejkolwiek sekwencji ucieczki. Na szczęście, jeśli dwa ciągi są zakodowane obok siebie, zostaną potraktowane jako jeden ciąg. Sekwencję ucieczki można wstawić pomiędzy, jak to zrobiono powyżej. Sekwencja ucieczki zostałaby rozszerzona. Tak więc dane wyjściowe stają się:



Turystyka w Egipcie jest jedną z wiodących gałęzi gospodarki kraju.

Ciąg według podwójnych cytatów

W przypadku podwójnych cudzysłowów sekwencje specjalne również nie są interpretowane, ale zmienne są interpretowane. Poniższy kod ilustruje to:

myVar=Turystykaw Egipt jest jednym z kraju 's wiodących gospodarczych branż.
wyrzucił $myVar

Dane wyjściowe to:

Turystyka w Egipcie jest jedną z wiodących gałęzi gospodarki kraju.

Uwaga: apostrof również używał sekwencji ucieczki przestrzeni.

W tym artykule głównym typem ciągu znaków jest ciąg w pojedynczych cudzysłowach.

Podstawy wyrażeń regularnych

Regex

Rozważ ten ciąg:

Ten świat nie jest tak naprawdę naszym domem.

Niech świat będzie podciągiem zainteresowania. Następnie duży ciąg (cały ciąg) nazywany jest ciągiem docelowym lub po prostu celem. „Świat” w cudzysłowie nazywa się wyrażeniem regularnym lub po prostu wyrażeniem regularnym. Treść, świat, jest w tym przypadku wzorcem.

Proste dopasowanie

W poniższym kodzie, jeśli słowo „świat” zostanie znalezione w celu, powiedzielibyśmy, że słowo zostało dopasowane.

P=„Ten świat nie jest tak naprawdę naszym domem”.
reg='świat'
Jeśli [[ $ str= ~$reg ]];następnie
wyrzuciłznaleziony
w przeciwnym razie
wyrzuciłnie znaleziono
być

=~ , który jest operatorem przypisania, po którym następuje ~ , jest nazywany operatorem wiązania. Warunek sprawdza, czy wzorzec jest dopasowany w ciągu docelowym. Jeśli podciąg odpowiadający wzorcowi zostanie znaleziony w celu, zostanie wyświetlona instrukcja echo. Jeśli nie zostanie znaleziony, echo instrukcja echo nie zostanie znaleziona. Dane wyjściowe dla tego kodu to:

znaleziony

Jako wzorzec, świat, znajduje się w celu. Zwróć uwagę, że odstępy po [[ i przed ]] zostały zachowane.

Wzór

W powyższym kodzie „świat” w cudzysłowie jest wyrażeniem regularnym, podczas gdy sam świat jest wzorcem. To jest prosty wzór. Jednak większość wzorów nie jest taka prosta. Wzorzec to charakterystyka odnalezionego podciągu. I tak wzór Bash wykorzystuje pewne metaznaki. Metaznak to postać dotycząca innych postaci. Na przykład wzór Bash używa następujących metaznaków:

^ $ . * +? () [] {} |

Wyrażenie regularne można również wpisać w nawiasach podwójnych warunku. Ale nie musi być w cudzysłowie. Tak więc w tym przypadku jest to dosłownie wzór.

Klasy postaci

Nawiasy kwadratowe

Znaleziono wynik następującego kodu, co oznacza, że ​​nastąpiło dopasowanie:

P=- Kot wszedł do komnaty.
Jeśli [[ $ str= ~[cbr]w]];następnie
wyrzuciłznaleziony
być

Wzorzec [cbr]at pasuje do cat, który zaczyna się od „c”, a który jest kontynuowany i kończy się na. [cbr]at oznacza dopasowanie „c” lub „b” lub „r”, po którym następuje at.

Znaleziono wynik następującego kodu, co oznacza, że ​​nastąpiło dopasowanie:

P=- Nietoperz wszedł do komory.
Jeśli [[ $ str= ~[cbr]w]];następnie
wyrzuciłznaleziony
być

Wzór [cbr]at ma dopasowany nietoperz, który zaczyna się od „b”, a który jest kontynuowany i kończy się na. [cbr]at oznacza dopasowanie „c” lub „b” lub „r”, po którym następuje at.

Znaleziono wynik następującego kodu, co oznacza, że ​​nastąpiło dopasowanie:

P=- Szczur wszedł do komory.
Jeśli [[ $ str= ~[cbr]w]];następnie
wyrzuciłznaleziony
być

Wzorzec [cbr]at dopasował szczura, który zaczyna się od „r”, a który jest kontynuowany i kończy się na.

W powyższych przykładach kodu programista nie wie, czy w łańcuchu docelowym istnieje kot, nietoperz lub szczur. Ale wie, że podciąg zaczyna się od „c”, „b” lub „r”, a następnie jest kontynuowany i kończy się na. Nawiasy kwadratowe we wzorcu pozwalają różnym możliwym znakom na dopasowanie jednego znaku w pozycji względem innych w miejscu docelowym. Tak więc nawiasy kwadratowe zawierają zestaw znaków, z których jeden jest dopasowany do podłańcucha. Wreszcie dopasowywany jest cały podciąg.

Zakres znaków

W powyższym kodzie [cbr] to klasa. Nawet jeśli „c” lub „b” lub „r” odpowiada pojedynczemu znakowi, jeśli po tym nastąpi natychmiastowe dopasowanie, wzorzec nie dopasuje niczego.

Cóż, istnieją pewne zakresy, które tworzą klasę. Na przykład od 0 do 9 cyfr tworzy klasę, [0-9] z uwzględnieniem 0 i 9. Małe litery „a” do „z” tworzą klasę [a-z] z uwzględnieniem „a” i „z”. Wielkie litery „A” do „Z” tworzą klasę [A-Z] z uwzględnieniem „A” i „Z”. Z klasy jest to jeden ze znaków, które pasują do jednego znaku w ciągu.

Poniższy kod tworzy dopasowanie:

Jeśli [[ „ID8id”= ~[0-9] ]];następnie
wyrzuciłznaleziony
być

Tym razem celem jest dosłowny łańcuch w warunku. 8, która jest jedną z możliwych liczb w zakresie [0-9], pasuje do 8 w ciągu „ID8id”. Powyższy kod jest odpowiednikiem:

Jeśli [[ „ID8id”= ~[0123456789] ]];następnie
wyrzuciłznaleziony
być

Tutaj wszystkie możliwe liczby zostały zapisane we wzorcu, więc nie ma łącznika.

W poniższym kodzie uzyskuje się dopasowanie:

Jeśli [[ „ID8iD”= ~[a-z] ]];następnie
wyrzuciłznaleziony
być

Dopasowanie odbywa się między małymi literami „i” z zakresu, [a-z] i małą literą „i” w ciągu docelowym, „ID8iD”.

Pamiętaj: zakres to klasa. Klasa może być częścią większego wzorca. Tak więc we wzorcu tekst może znajdować się przed i/lub za zajęciami. Poniższy kod ilustruje to:

Jeśli [[ „ID8id to identyfikator”=~ ID[0-9]NS ]];następnie
wyrzuciłznaleziony
być

Dane wyjściowe to: znaleziono. „ID8id” ze wzorca pasuje do „ID8id” w ciągu docelowym.

Negacja

Dopasowanie nie jest uzyskiwane z następującego kodu:

Jeśli [[ '0123456789101112'= ~[^0-9] ]];następnie
wyrzuciłznaleziony
w przeciwnym razie
wyrzuciłnie znaleziono
być

Dane wyjściowe to:

nie znaleziono

Bez znaku ^ przed zakresem, w nawiasach kwadratowych, zero zakresu odpowiadałoby pierwszemu zerowi ciągu docelowego. Tak więc ^ przed zakresem (lub opcjonalnymi znakami) neguje klasę.

Poniższy kod tworzy dopasowanie, ponieważ warunek brzmi: dopasuj dowolny znak niecyfrowy w dowolnym miejscu celu:

Jeśli [[ „ABCDEFGHIJ”= ~[^0-9] ]];następnie
wyrzuciłznaleziony
w przeciwnym razie
wyrzuciłnie znaleziono
być

Wynik to: find .

[^0-9] oznacza niecyfrę, więc [^0-9] jest negacją [0-9] .

[^a-z] oznacza literę inną niż mała, więc [^a-z] jest negacją [a-z] .

[^A-Z] oznacza literę inną niż wielka, więc [^A-Z] jest negacją [A-Z] .

Dostępne są inne negacje.

Okres (.) we wzorcu

Kropka (.) we wzorcu pasuje do dowolnego znaku, w tym samego siebie. Rozważ następujący kod:

Jeśli [[ '6759WXY.A3'= ~ 7,9 W.Y.A]];następnie
wyrzuciłznaleziony
być

Dane wyjściowe kodu zostały znalezione, ponieważ pozostałe znaki są zgodne. Jedna kropka pasuje do „5”; kolejna kropka pasuje do „X”; a ostatnia kropka pasuje do kropki.

Dopasowana alternatywa

Rozważ to zdanie jako łańcuch docelowy:

W klatce znajdują się ptaki różnych typów.

Ktoś może chcieć wiedzieć, czy ten cel ma gołębia, pawia czy orła. Można użyć następującego kodu:

P=— W klatce są różne rodzaje pawi.
Jeśli [[ $ str=~ gołąb|paw|Orzeł]];następnie
wyrzuciłznaleziony
w przeciwnym razie
wyrzuciłnie znaleziono
być

Wynik jest znaleziony. Metaznak alternatywny, | został zatrudniony. Mogą być dwie, trzy, cztery i więcej alternatyw. To, co pasuje w tym kodzie, to „paw”.

Grupowanie

W poniższym schemacie do grupowania znaków użyto nawiasów:

scena (tancerka)

Grupa tutaj to tancerz sceniczny otoczony metaznakami (i). (tancerz) to podgrupa, podczas gdy scena (tancerz) to cała grupa. Rozważ następujące:

(tancerka jest niesamowita)

Tutaj podgrupa lub podciąg brzmi: tancerz jest niesamowity.

Podciągi ze wspólnymi częściami

Interesariusz to osoba zainteresowana biznesem. Wyobraź sobie firmę z witryną internetową stake.com. Wyobraź sobie, że w komputerze znajduje się jeden z następujących ciągów docelowych:

Strona internetowa stake.com przeznaczona jest dla biznesu.;

Jest interesariusz.;

Interesariusz pracuje dla stake.com.;

Niech którykolwiek z tych ciągów będzie celem. Programista może chcieć wiedzieć, czy w jakimkolwiek ciągu docelowym znajduje się stake.com lub udziałowiec. Jego wzór byłby:

udział.com|interesariusz

za pomocą naprzemiennego.

stawka została wpisana dwukrotnie w tych dwóch słowach. Można tego uniknąć, wpisując wzór w następujący sposób:

udział(.com|posiadacz)

.com|holder jest w tym przypadku podgrupą.

Uwaga: użycie w tym przypadku znaku naprzemiennego. stake.com lub interesariusz nadal będą przeszukiwane. Znaleziono wynik następującego kodu:

P=„Strona internetowa stake.com jest przeznaczona dla biznesu”.
Jeśli [[ $ str=~ stawka(.z|uchwyt) ]];następnie
wyrzuciłznaleziony
być

Dopasowany podłańcuch to stake.com.

Predefiniowana tablica BASH_REMATCH

BASH_REMATCH to predefiniowana tablica. Załóżmy, że wzór ma grupy. Cała dopasowana grupa trafia do komórki o indeksie 0 tej tablicy. Pierwsza dopasowana podgrupa trafia do komórki dla indeksu 1; druga dopasowana podgrupa przechodzi do komórki dla indeksu 2 i tak dalej. Poniższy kod pokazuje, jak używać tej tablicy:

P=– Przybyła tancerka sceniczna.
Jeśli [[ $ str=~ etap(tancerz) ]];następnie
wyrzuciłznaleziony
być

dlaiw ${!BASH_REMATCH[@]};robić
printf '${BASH_REMATCH[i]}, '
Gotowe
wyrzucił

Dane wyjściowe to:

znaleziony
tancerz sceniczny, tancerz,

Cała grupa to tancerz sceniczny. Jest tylko jedna podgrupa, którą jest tancerz.

Uwaga: spacja we wzorze została opuszczona.

Dopasowywanie niezależności wielkich/mniejszych liter

Jak wyjaśniono powyżej, w dopasowaniu rozróżniana jest wielkość liter. Dopasowanie można przeprowadzić niezależnie od sprawy. Ilustruje to następujący kod:

sklepy -snocasematch

P=„Lubimy dobrą muzykę”.
Jeśli [[ $ str=~ Dobrze]];następnie
wyrzuciłznaleziony
być

sklepy -unocasematch

Dane wyjściowe to: znaleziono. Wzorzec jest dobry. Dopasowany podciąg jest „dobry”. Zauważ, że opcja nocasematch została włączona na początku segmentu kodu i wyłączona na końcu segmentu kodu.

Długość struny

Składnia do uzyskania długości ciągu to:

${#PARAMETR}

Przykład:

P=„Lubimy dobrą muzykę”.
wyrzucił $ {# str.}

Wyjście to: 19.

Redukcja ciągu

Składnie redukcji ciągów to:

${PARAMETR:PRZESUNIĘCIE}
${PARAMETR:PRZESUNIĘCIE:DŁUGOŚĆ}

gdzie liczenie dla PRZESUNIĘCIA rozpoczyna się od zera.

Poniższy przykład pokazuje, jak usunąć pierwszych 11 znaków ciągu:

P=„Zawsze tańczę do dobrej muzyki”.
wyrzucił $ {str: 10}

Dane wyjściowe to:

do dobrej muzyki.

Liczenie na DŁUGOŚĆ zaczyna się od następnego znaku. Poniższy kod pokazuje, jak można zezwolić na część w ciągu:

P=„Zawsze tańczę do dobrej muzyki”.
wyrzucił $ {str: 10: 6}

Dane wyjściowe to:

ance t

Pierwsze 11 znaków zostało usuniętych; kolejnych 6 znaków było dozwolonych, a reszta znaków została automatycznie usunięta.

Wyszukaj i zamień

Po znalezieniu podciągu można go zastąpić innym podciągiem. Składnia do tego to:

gdzie=${PARAMETR/WZÓR/ZAMIANA}
gdzie=${PARAMETR//WZÓR/ZAMIANA}
gdzie=${PARAMETR/WZÓR}
gdzie=${PARAMETR//WZÓR}

W przypadku pierwszej składni z pojedynczym ukośnikiem zastępowane jest tylko pierwsze dopasowanie. Przykład:

P=- W komnacie jest szczur, nietoperz i kot.
Prawidłowy=${str/[cbr]od/duża krowa}
wyrzucił $ str
wyrzucił $ ret

Dane wyjściowe to:

W komnacie jest szczur, nietoperz i kot.
W komnacie jest duża krowa, nietoperz i kot.

W przypadku drugiej składni z podwójnymi ukośnikami wszystkie wystąpienia dopasowania są zastępowane. Przykład:

P=- W komnacie jest szczur, nietoperz i kot.
Prawidłowy=${str//[cbr]u/duża krowa}
wyrzucił $ str
wyrzucił $ ret

Dane wyjściowe to:

W komnacie jest szczur, nietoperz i kot.
W komorze jest duża krowa, duża krowa i duża krowa.

W przypadku trzeciej składni z pojedynczym ukośnikiem nie można zastąpić pierwszego i jedynego dopasowania.

Ponadto usuwany jest pierwszy znaleziony podciąg. Przykład:

P=- W komnacie jest szczur, nietoperz i kot.
Prawidłowy=${str/[cbr]at}
wyrzucił $ str
wyrzucił $ ret

W przypadku czwartej składni z podwójnymi ukośnikami nie można zastąpić wszystkich dopasowań. Ponadto wszystkie znalezione podciągi są usuwane. Przykład:

P=- W komnacie jest szczur, nietoperz i kot.
Prawidłowy=${str//[cbr]at}
wyrzucił $ str
wyrzucił $ ret

Dane wyjściowe to:

W komnacie jest szczur, nietoperz i kot.
W komorze znajduje się , a i .

Wniosek

Aby sprawdzić, czy ciąg ma podciąg w Bash, należy użyć funkcji Pattern Matching. Dopasowywanie wzorców odbywa się nie tylko w warunkach podwójnych nawiasów [[ . . . ]]. Może również mieć miejsce w rozwinięciu parametrów, z jego ${. . .}. Dzięki rozszerzaniu parametrów możliwe jest uzyskanie podciągu za pomocą indeksów.

To, co zostało przedstawione w tym artykule, to najbardziej krytyczne punkty w dopasowywaniu wzorców. Jest ich więcej! Jednak to, co czytelnik powinien dalej studiować, to rozszerzenie nazwy pliku.