Saya ingin mengulang setiap pola yang ditemukan dan memiliki akses ke grup tangkapan yang berbeda di dalam loop, mungkin dengan grep
atau awk
(Saya ingin tetap bersama mereka jika memungkinkan untuk menghindari mempelajari yang ketiga, tetapi jika benar-benar perlu, saya akan mempelajari yang lain!)
Melakukan sesuatu seperti:
awk-or-grep -E '(blah(.*)hello=(.*))' sampletext | while read -r l; do
echo $0 #1st capture group
echo $1 #2nd catpure group
dosomethingwith $2 #3rd capture group
done
ada?
Contoh teks:
blah12687hello=123
nothingthatmatches
blah3211hello=123456
blah15butnottheotherpattern
Dengan loop yang disebutkan sebelumnya, seharusnya menampilkan:
blah12687hello=123
12687
<it should run the command dosomethingwith 123>
blah3211hello=123456
3211
<it should run the command dosomethingwith 123456>
Jawaban yang Diterima:
bash
shell dengan sendirinya menyediakan cara untuk melakukan proses pencocokan ekspresi reguler kelompok yang ditangkap sesuai kebutuhan.
=~
operator dalam ekspresi pengujian tanda kurung ganda, [[
dengan string yang cocok di sisi kiri operator dan ekspresi reguler sebagai operan kanan.
if [[ "$str" =~ $re ]]; then
Jika ekspresi cocok dengan string, bagian string yang cocok disimpan di BASH_REMATCH
array yang dapat dilingkarkan untuk mengakses grup yang diambil secara individual. Status keluarnya adalah jika regexp cocok,
1
jika tidak, dan 2
jika ekspresi tidak valid.
Sejauh menyangkut contoh Anda, dengan asumsi Anda memiliki baris input yang disimpan dalam array dan kata-kata blah
dan hello
adalah pola tetap
#!/usr/bin/env bash
exampleStr=('blah12687hello=123' 'nothingthatmatches' 'blah3211hello=123456' 'blah15butnottheotherpattern')
re='blah([[:digit:]]+)hello=([[:digit:]]+)'
for str in "${exampleStr[@]}"; do
if [[ "$str" =~ $re ]]; then
for group in "${BASH_REMATCH[@]}"; do
printf "%s\n" "$group"
done
else
printf "No match \n"
fi
done
Seperti yang Anda lihat pada kode di atas, setelah kami mencocokkan regex dengan true, kami dapat mengulang BASH_REMATCH
array untuk mencetak setiap grup yang diambil. Output skrip keseluruhan akan menjadi seperti
blah12687hello=123 # Value of BASH_REMATCH[0]
12687 # Value of BASH_REMATCH[1]
123 # Value of BASH_REMATCH[2]
Regex not matches.
blah3211hello=123456
3211
123456
Regex not matches.
Seperti yang Anda lihat BASH_REMATCH[0]
selalu berisi bagian dari string yang berhasil dicocokkan oleh ekspresi reguler, dan grup yang diambil secara individual dapat diakses dari indeks 1
maju. Anda dapat menulis logika khusus untuk memproses setiap grup yang diambil yang merupakan tujuan awal Anda.
Jika Anda tertarik untuk membaca input file, cukup gunakan while
loop dengan input re-direction pada file yang akan diproses
while IFS= read -r line; do
if [[ "$line" =~ $re ]]; then
for group in "${BASH_REMATCH[@]}"; do
printf "%s\n" "$group"
done
else
printf "No match \n"
fi
done < inputFile.txt