Ekspresi reguler untuk string yang berisi satu kata tetapi tidak kata lainnya


103

Saya sedang menyiapkan beberapa sasaran di Google Analytics dan dapat menggunakan sedikit bantuan regex.

Katakanlah saya memiliki 4 URL

http://www.anydotcom.com/test/search.cfm?metric=blah&selector=size&value=1
http://www.anydotcom.com/test/search.cfm?metric=blah2&selector=style&value=1
http://www.anydotcom.com/test/search.cfm?metric=blah3&selector=size&value=1
http://www.anydotcom.com/test/details.cfm?metric=blah&selector=size&value=1

Saya ingin membuat ekspresi yang akan mengidentifikasi URL apa pun yang berisi string selector = size tetapi TIDAK berisi details.cfm

Saya tahu bahwa untuk menemukan string yang TIDAK berisi string lain, saya dapat menggunakan ungkapan ini:

(^((?!details.cfm).)*$)

Tapi, saya tidak yakin bagaimana menambahkan bagian selector = size .

Bantuan apa pun akan sangat dihargai!

Jawaban:


144

Ini harus melakukannya:

^(?!.*details\.cfm).*selector=size.*$

^.*selector=size.*$harus cukup jelas. Bit pertama, (?!.*details.cfm)adalah pandangan ke depan negatif: sebelum mencocokkan string itu memeriksa bahwa string tidak mengandung "details.cfm" (dengan sejumlah karakter sebelumnya).


8
FYI, periksa regexr.com untuk cara yang bagus untuk menguji ekspresi ini.
— Joshua Pinter

Selalu lupakan tentang pandangan negatif dan ini sangat berguna
— Alexei Blue

"http://www.anydotcom.com/test/search.cfm?metric=blah&selector=sized&value=1" =~ /^(?!.*details\.cfm).*selector=size.*$/ #=> 0salah. (Perhatikan string berisi "...selector=sized...".) Juga, mengapa .*$di akhir?
— Cary Swoveland

4

regex bisa jadi (sintaks perl):

`/^[(^(?!.*details\.cfm).*selector=size.*)|(selector=size.*^(?!.*details\.cfm).*)]$/`

Ini adalah regex yang rusak, tanda kurung siku mengubah semua urutan pola menjadi kombinasi karakter individual.
— Wiktor Stribiżew

2
^(?=.*selector=size)(?:(?!details\.cfm).)+$

Jika mesin regex Anda mendukung pengukur posesif (meskipun saya curiga Google Analytics tidak), saya rasa ini akan bekerja lebih baik untuk kumpulan masukan yang besar:

^[^?]*+(?<!details\.cfm).*?selector=size.*$

Ini mengasumsikan selector=sizeselalu sebelumnya details.cfm, yang tidak terjadi di url terakhir.
— Kobi

Hanya untuk menjernihkan ini, bukan aku. Saya tidak bisa melihat mengapa seseorang akan memilih dua jawaban di sini, keduanya benar.
— Kobi

@Kobi: Ini seharusnya melihat ke depan, dikoreksi. Oh, dan omong-omong, saya tidak curiga itu adalah suara negatif Anda.
— Tomalak

0

Saya sedang mencari cara untuk menghindari --line-bufferedekor dalam situasi yang sama karena solusi OP dan Kobi bekerja sangat baik untuk saya. Dalam kasus saya tidak termasuk baris dengan "bot" atau "spider" sementara menyertakan ' / '(untuk dokumen root saya).

Perintah asli saya:

tail -f mylogfile | grep --line-buffered -v 'bot\|spider' | grep ' / '

Sekarang menjadi (dengan -Psaklar perl):

tail -f mylogfile | grep -P '^(?!.*(bot|spider)).*\s\/\s.*$'
Dengan menggunakan situs kami, Anda mengakui telah membaca dan memahami Kebijakan Cookie dan Kebijakan Privasi kami.
Licensed under cc by-sa 3.0 with attribution required.