Saya setuju bahwa alat yang tepat untuk mem-parsing XML dan terutama HTML adalah parser dan bukan mesin ekspresi reguler. Namun, seperti yang telah ditunjukkan orang lain, terkadang menggunakan regex lebih cepat, lebih mudah, dan menyelesaikan pekerjaan jika Anda tahu format data.
Microsoft sebenarnya memiliki bagian Praktik Terbaik untuk Ekspresi Reguler di .NET Framework dan secara khusus berbicara tentang Mempertimbangkan Sumber Input .
Ekspresi Reguler memang memiliki batasan, tetapi sudahkah Anda mempertimbangkan yang berikut?
Kerangka .NET adalah unik ketika datang ke ekspresi reguler karena mendukung Balancing Group Definition .
Untuk alasan ini, saya yakin Anda BISA parsing XML menggunakan ekspresi reguler. Namun perlu dicatat, itu harus XML yang valid ( browser sangat memaafkan HTML dan memungkinkan sintaks XML yang buruk di dalam HTML ). Ini dimungkinkan karena "Balancing Group Definition" akan memungkinkan mesin ekspresi reguler untuk bertindak sebagai PDA.
Kutipan dari artikel 1 yang dikutip di atas:
.NET Regular Expression Engine
Seperti yang dijelaskan di atas, konstruksi seimbang yang tepat tidak dapat dijelaskan dengan ekspresi reguler. Namun, mesin ekspresi reguler .NET menyediakan beberapa konstruksi yang memungkinkan konstruksi seimbang untuk dikenali.
(?<group>)
- Mendorong hasil yang ditangkap pada stack penangkapan dengan grup nama.
(?<-group>)
- Munculkan tangkapan paling atas dengan grup nama dari tumpukan penangkapan.
(?(group)yes|no)
- cocok dengan bagian ya jika ada grup dengan grup nama jika tidak cocok dengan bagian.
Konstruksi ini memungkinkan ekspresi reguler .NET untuk meniru PDA terbatas dengan dasarnya memungkinkan versi sederhana dari operasi stack: push, pop dan kosong. Operasi sederhana cukup banyak setara dengan kenaikan, penurunan dan dibandingkan dengan masing-masing nol. Ini memungkinkan .NET regular expression engine untuk mengenali subset dari bahasa bebas konteks, khususnya yang hanya memerlukan penghitung sederhana. Hal ini pada gilirannya memungkinkan untuk ekspresi reguler .NET non-tradisional untuk mengenali konstruksi seimbang yang tepat.
Pertimbangkan ungkapan reguler berikut:
(?=<ul\s+id="matchMe"\s+type="square"\s*>)
(?>
<!-- .*? --> |
<[^>]*/> |
(?<opentag><(?!/)[^>]*[^/]>) |
(?<-opentag></[^>]*[^/]>) |
[^<>]*
)*
(?(opentag)(?!))
Gunakan bendera:
- Garis tunggal
- IgnorePatternWhitespace (tidak perlu jika Anda menutup regex dan menghapus semua spasi putih)
- IgnoreCase (tidak perlu)
Dijelaskan Ekspresi Reguler (sebaris)
(?=<ul\s+id="matchMe"\s+type="square"\s*>) # match start with <ul id="matchMe"...
(?> # atomic group / don't backtrack (faster)
<!-- .*? --> | # match xml / html comment
<[^>]*/> | # self closing tag
(?<opentag><(?!/)[^>]*[^/]>) | # push opening xml tag
(?<-opentag></[^>]*[^/]>) | # pop closing xml tag
[^<>]* # something between tags
)* # match as many xml tags as possible
(?(opentag)(?!)) # ensure no 'opentag' groups are on stack
Anda dapat mencobanya di Penguji Ekspresi Reguler Reguler .NET yang Lebih Baik .
Saya menggunakan sumber sampel:
<html>
<body>
<div>
<br />
<ul id="matchMe" type="square">
<li>stuff...</li>
<li>more stuff</li>
<li>
<div>
<span>still more</span>
<ul>
<li>Another >ul<, oh my!</li>
<li>...</li>
</ul>
</div>
</li>
</ul>
</div>
</body>
</html>
Ini menemukan kecocokan:
<ul id="matchMe" type="square">
<li>stuff...</li>
<li>more stuff</li>
<li>
<div>
<span>still more</span>
<ul>
<li>Another >ul<, oh my!</li>
<li>...</li>
</ul>
</div>
</li>
</ul>
meskipun sebenarnya keluar seperti ini:
<ul id="matchMe" type="square"> <li>stuff...</li> <li>more stuff</li> <li> <div> <span>still more</span> <ul> <li>Another >ul<, oh my!</li> <li>...</li> </ul> </div> </li> </ul>
Terakhir, saya sangat menikmati artikel Jeff Atwood: Parsing Html The Cthulhu Way . Cukup lucu, mengutip jawaban atas pertanyaan ini yang saat ini memiliki lebih dari 4k suara.