Saya memiliki dua daftar dengan objek berbeda di dalamnya.
List<Object1> list1;
List<Object2> list2;
Saya ingin memeriksa apakah elemen dari list1 ada di list2, berdasarkan atribut tertentu (Object1 dan Object2 memiliki (antara lain), satu atribut bersama (dengan tipe Long), bernama atributSame).
sekarang, saya melakukannya seperti ini:
boolean found = false;
for(Object1 object1 : list1){
for(Object2 object2: list2){
if(object1.getAttributeSame() == object2.getAttributeSame()){
found = true;
//also do something
}
}
if(!found){
//do something
}
found = false;
}
Tetapi menurut saya ada cara yang lebih baik dan lebih cepat untuk melakukan ini :) Dapatkah seseorang melamarnya?
Terima kasih!
Jawaban:
Jika Anda hanya perlu menguji persamaan dasar, ini dapat dilakukan dengan JDK dasar tanpa mengubah daftar masukan dalam satu baris
Jika Anda perlu menguji properti tertentu, itu lebih sulit. Saya akan merekomendasikan, secara default,
... yang mengumpulkan nilai-nilai yang berbeda
list2
dan menguji setiap nilailist1
untuk keberadaannya.sumber
list1
ke aSet
sebelum membandingkan, Anda akan mendapatkan O (n) + O (m), yaitu, O (n + m), dengan biaya tambahan RAM; ini soal memilih antara kecepatan atau memori.Anda dapat menggunakan Apache Commons CollectionUtils :
Ini mengasumsikan bahwa Anda telah membebani dengan benar fungsionalitas yang sama untuk objek kustom Anda.
sumber
Untuk mempersingkat logika Narendra, Anda dapat menggunakan ini:
sumber
list1.stream().anyMatch(list2::contains);
Ada salah satu metode dari
Collection
bernamaretainAll
tetapi memiliki beberapa efek samping untuk Anda referensiItu seperti
sumber
Jawaban Loius benar, saya hanya ingin menambahkan contoh:
sumber
cara yang lebih cepat akan membutuhkan ruang tambahan.
Sebagai contoh:
letakkan semua item dalam satu daftar ke dalam HashSet (Anda harus mengimplementasikan fungsi hash sendiri untuk menggunakan object.getAttributeSame ())
Pergi melalui daftar lain dan periksa apakah ada item di HashSet.
Dengan cara ini setiap objek dikunjungi paling banyak sekali. dan HashSet cukup cepat untuk memeriksa atau memasukkan objek apa pun di O (1).
sumber
Menurut JavaDoc untuk
.contains(Object obj)
:Jadi jika Anda mengganti
.equals()
metode Anda untuk objek yang Anda berikan, Anda seharusnya bisa melakukan:if(list1.contains(object2))...
Jika elemen akan unik (mis. Memiliki atribut berbeda) Anda dapat menimpa
.equals()
dan.hashcode()
dan menyimpan semuanya diHashSets
. Ini akan memungkinkan Anda untuk memeriksa apakah satu berisi elemen lain dalam waktu yang konstan.sumber
untuk membuatnya lebih cepat, Anda bisa menambahkan jeda; dengan cara itu loop akan berhenti jika ditemukan disetel ke true:
Jika Anda ingin memiliki peta sebagai pengganti daftar dengan kunci atributSame, Anda dapat memeriksa lebih cepat untuk nilai dalam satu peta jika ada nilai yang sesuai di peta kedua atau tidak.
sumber
Bisakah Anda menentukan jenis data yang Anda pegang? apakah ini data besar? apakah sudah diurutkan? Saya pikir Anda perlu mempertimbangkan pendekatan efisiensi yang berbeda tergantung pada datanya.
Misalnya, jika data Anda besar dan tidak diurutkan, Anda dapat mencoba dan mengulang kedua daftar bersama-sama dengan index dan menyimpan setiap atribut list di list helper lainnya. lalu Anda dapat melakukan pemeriksaan silang dengan atribut saat ini di daftar pembantu.
semoga berhasil
diedit: dan saya tidak akan merekomendasikan overloading sama. itu berbahaya dan mungkin bertentangan dengan makna objek Anda.
sumber
org.springframework.util.CollectionUtils
sumber
Dengan
java 8
, kita bisa melakukan seperti di bawah ini untuk memeriksa apakah satu daftar berisi elemen daftar lainnyasumber
Jika Anda ingin memeriksa apakah suatu elemen ada dalam daftar, gunakan metode berisi.
sumber