Bash regex yakalama grubu


22

Birden çok alfanümerik değeri (bu sayı değişebilir) bir dizeden eşleştirmeye ve bunları bir bash yakalama grubu dizisine kaydetmeye çalışıyorum. Ancak, sadece ilk maçı alıyorum:

mystring1='<link rel="self" href="/unix//api/clouds/1/instances/1BBBBBB"/> dsf <link rel="self" href="/unix//api/clouds/1/instances/2AAAAAAA"/>'

regex='/instances/([A-Z0-9]+)'

[[ $mystring1 =~ $regex ]]

echo ${BASH_REMATCH[1]}
1BBBBBB

echo ${BASH_REMATCH[2]}

Gördüğünüz gibi, aradığım ilk değerle eşleşiyor, ikincisi değil.


1
Çıktısının üzerinden döngü ile memnun olur echo "$mystring1" | grep -oE '/instances/([A-Z0-9]+)'musunuz?
Jeff Schaller

4
Muhtemelen ünlüleri anlatmaya değer HTML'yi regex post ile ayrıştıramazsınız .
Dijital Travma

Yanıtlar:


22

Bash'ta global eşleşmeyi yapamamanız çok yazık. Bunu yapabilirsiniz:

global_rematch() { 
    local s=$1 regex=$2 
    while [[ $s =~ $regex ]]; do 
        echo "${BASH_REMATCH[1]}"
        s=${s#*"${BASH_REMATCH[1]}"}
    done
}
global_rematch "$mystring1" "$regex" 
1BBBBBB
2AAAAAAA

Bu, dizenin üstündeki eşleşen öneki keserek çalışır, böylece sonraki bölüm eşlenebilir. Dizeyi yok eder, ancak fonksiyonda yerel bir değişkendir, bu yüzden kimin umurunda.

Bir diziyi doldurmak için aslında bu işlevi kullanırdım:

$ mapfile -t matches < <( global_rematch "$mystring1" "$regex" )
$ printf "%s\n" "${matches[@]}"
1BBBBBB
2AAAAAAA

teşekkürler - bu uygulanabilir bir çözüme benziyor - sadece konu bash 3.2'de mevcut olmayan mapfile ...
Arthur Lyssenko


6

İkinci dizi değerini elde etmek için, regex'te ikinci bir parantez grubuna sahip olmanız gerekir:

mystring1='<link rel="self" href="/unix//api/clouds/1/instances/1BBBBBB"/> dsf <link rel="self" href="/unix//api/clouds/1/instances/2AAAAAAA"/>'

regex='/instances/([A-Z0-9]+).*/instances/([A-Z0-9]+)'

[[ $mystring1 =~ $regex ]]

$ echo ${BASH_REMATCH[1]}
1BBBBBB
$ echo ${BASH_REMATCH[2]}
2AAAAAAA

Sağol, bilinmeyen sayıda olası eşleşmeyle eşleşmek istiyorum.
Arthur Lyssenko,

1
Q'nuzu yükselttim çünkü diziye birden fazla eşleşme gelmesini bekledim, ancak aslında birden fazla parantez kümeniz olmadığı sürece görünmüyorlar.
Jeff Schaller
Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.