Ekspresi ekspresi reguler di Java, \\ s vs. \\ s +

96

Apa perbedaan antara dua ekspresi berikut?

x = x.replaceAll("\\s", "");
x = x.replaceAll("\\s+", "");
mpluse
sumber
3
Pengukur, baca di atasnya.
jn1kk

Jawaban:

88

Yang pertama cocok dengan satu spasi, sedangkan yang kedua cocok dengan satu atau banyak spasi. Mereka disebut pembilang ekspresi reguler, dan mereka melakukan kecocokan seperti ini (diambil dari dokumentasi ):

Greedy quantifiers
X?  X, once or not at all
X*  X, zero or more times
X+  X, one or more times
X{n}    X, exactly n times
X{n,}   X, at least n times
X{n,m}  X, at least n but not more than m times

Reluctant quantifiers
X?? X, once or not at all
X*? X, zero or more times
X+? X, one or more times
X{n}?   X, exactly n times
X{n,}?  X, at least n times
X{n,m}? X, at least n but not more than m times

Possessive quantifiers
X?+ X, once or not at all
X*+ X, zero or more times
X++ X, one or more times
X{n}+   X, exactly n times
X{n,}+  X, at least n times
X{n,m}+ X, at least n but not more than m times
Óscar López
sumber
20
Saya selalu menyukai bagaimana mereka memberikan deskripsi terpisah tentang versi serakah, enggan, dan posesif dari setiap pembilang, dan kemudian mengatakan hal yang persis sama tentang ketiganya. ;)
Alan Moore
60

Kedua replaceAllpanggilan tersebut akan selalu memberikan hasil yang sama, apapun xitu. Namun, penting untuk diperhatikan bahwa kedua ekspresi reguler itu tidak sama:

  • \\s - cocok dengan karakter spasi putih tunggal
  • \\s+ - mencocokkan urutan dari satu atau lebih karakter spasi.

Dalam hal ini, tidak ada bedanya, karena Anda mengganti semuanya dengan string kosong (meskipun akan lebih baik menggunakan \\s+dari sudut pandang efisiensi). Jika Anda mengganti dengan string yang tidak kosong, keduanya akan berperilaku berbeda.

arshajii
sumber
Tulis baris pertama Anda, Jika x adalah "Pesan Domain Anda Dan Dapatkan \ n \ n \ n \ n \ n \ n Online Sekarang." Akankah keduanya menghasilkan hasil yang sama?
sofs1
3
@ user3705478 Keduanya akan menghasilkan hasil yang sama, meskipun akan ada beberapa spasi setelah satu sama lain. Perbedaannya terletak pada cara penanganannya. Jika Anda memiliki grup (misalnya) 3 spasi yang langsung mengikuti satu sama lain, \\ s + mengambil grup itu dan mengubahnya menjadi "", sedangkan \\ s akan memproses setiap spasinya sendiri.
Dennie
11

Pertama-tama Anda perlu memahami bahwa hasil akhir dari kedua pernyataan akan sama yaitu menghapus semua spasi dari string yang diberikan.

Namun x.replaceAll("\\s+", "");akan lebih efisien cara pemangkasan spasi (jika string dapat memiliki beberapa spasi yang berdekatan) karena berpotensi lebih sedikit tidak ada penggantian karena fakta bahwa regex \\s+cocok dengan 1 atau lebih spasi sekaligus dan menggantinya dengan string kosong.

Jadi meskipun Anda mendapatkan hasil yang sama dari keduanya, lebih baik gunakan:

x.replaceAll("\\s+", "");
anubhava.dll
sumber
2

Regex pertama akan cocok dengan satu karakter spasi. Regex kedua akan dengan enggan mencocokkan satu atau lebih karakter spasi. Untuk sebagian besar tujuan, kedua ekspresi reguler ini sangat mirip, kecuali pada kasus kedua, ekspresi reguler dapat mencocokkan lebih banyak string, jika hal itu mencegah pencocokan ekspresi reguler gagal. dari http://www.coderanch.com/t/570917/java/java/regex-difference

evgenyl.dll
sumber
Gores kata "dengan enggan". Pertanyaan ini tentang \s+, bukan \s+?seperti pertanyaan lainnya.
Alan Moore