Panduan untuk Apache Commons MultiValuedMap

1. Gambaran keseluruhan

Dalam tutorial ringkas ini, kita akan melihat antara muka MultiValuedMap yang disediakan di perpustakaan Apache Commons Collections .

MultiValuedMap menyediakan API sederhana untuk memetakan setiap kunci ke koleksi nilai di Java. Ini adalah penerus kepada org.apache.commons.collections4.MultiMap, yang tidak digunakan lagi dalam Commons Collection 4.1.

2. Ketergantungan Maven

Untuk projek Maven, kita perlu menambahkan pergantungan commons-koleksi4 :

 org.apache.commons commons-collections4 4.2 

3. Menambah Elemen ke dalam MultiValuedMap

Kita boleh menambahkan elemen menggunakan kaedah put and putAll .

Mari mulakan dengan membuat contoh MultiValuedMap :

MultiValuedMap map = new ArrayListValuedHashMap();

Seterusnya, mari kita lihat bagaimana kita dapat menambahkan elemen satu demi satu menggunakan kaedah put :

map.put("fruits", "apple"); map.put("fruits", "orange");

Di samping itu, mari kita tambahkan beberapa elemen menggunakan kaedah putAll , yang memetakan kunci kepada beberapa elemen dalam satu panggilan:

map.putAll("vehicles", Arrays.asList("car", "bike")); assertThat((Collection) map.get("vehicles")) .containsExactly("car", "bike");

4. Mengambil Elemen dari MultiValuedMap

MultiValuedMap menyediakan kaedah untuk mengambil kunci, nilai, dan pemetaan nilai-kunci. Mari kita perhatikan masing-masing.

4.1. Dapatkan Semua Nilai Kekunci

Untuk mendapatkan semua nilai yang dikaitkan dengan kunci, kita dapat menggunakan kaedah get , yang mengembalikan Koleksi :

assertThat((Collection) map.get("fruits")) .containsExactly("apple", "orange");

4.2. Dapatkan Semua Pemetaan Nilai Utama

Atau, kita boleh menggunakan kaedah entri untuk mendapatkan Koleksi semua pemetaan nilai kunci yang terdapat dalam peta:

Collection
    
      entries = map.entries();
    

4.3. Dapatkan Semua Kunci

Terdapat dua kaedah untuk mengambil semua kunci yang terdapat dalam MultiValuedMap.

Mari gunakan kaedah kunci untuk mendapatkan paparan kunci pelbagai tetapan :

MultiSet keys = map.keys(); assertThat(keys).contains("fruits", "vehicles");

Sebagai alternatif, kita boleh mendapatkan pandangan Set kunci menggunakan kaedah keySet :

Set keys = map.keySet(); assertThat(keys).contains("fruits", "vehicles");

4.4. Dapatkan Semua Nilai Peta

Akhirnya, jika kita ingin mendapatkan pandangan Koleksi semua nilai yang terdapat dalam peta, kita dapat menggunakan kaedah nilai :

Collection values = map.values(); assertThat(values).contains("apple", "orange", "car", "bike");

5. Mengeluarkan Elemen dari MultiValuedMap

Sekarang, mari kita lihat semua kaedah untuk membuang elemen dan pemetaan nilai kunci.

5.1. Buang Semua Elemen yang Dipetakan ke Kekunci

Pertama, mari kita lihat cara membuang semua nilai yang berkaitan dengan kunci yang ditentukan menggunakan kaedah buang :

Collection removedValues = map.remove("fruits"); assertThat(map.containsKey("fruits")).isFalse(); assertThat(removedValues).contains("apple", "orange");

Kaedah ini mengembalikan pandangan Koleksi dari nilai yang dikeluarkan.

5.2. Keluarkan Pemetaan Nilai Utama Tunggal

Sekarang, anggaplah kita mempunyai kunci yang dipetakan untuk beberapa nilai, tetapi kita ingin membuang hanya satu dari nilai yang dipetakan, meninggalkan yang lain. Kita boleh melakukannya dengan mudah menggunakan kaedah removeMapping :

boolean isRemoved = map.removeMapping("fruits","apple"); assertThat(map.containsMapping("fruits","apple")).isFalse();

5.3. Buang Semua Pemetaan Nilai Utama

Dan akhirnya, kita dapat menggunakan kaedah yang jelas untuk membuang semua pemetaan dari peta:

map.clear(); assertThat(map.isEmpty()).isTrue();

6. Memeriksa Elemen dari MultiValuedMap

Next, let's take a look at the various methods for checking whether a specified key or value exists in our map.

6.1. Check If a Key Exists

To find out whether our map contains a mapping for a specified key, we can use the containsKey method:

assertThat(map.containsKey("vehicles")).isTrue();

6.2. Check If a Value Exists

Next, suppose we want to check if at least one key in our map contains a mapping for a particular value. We can do this using the containsValue method:

assertThat(map.containsValue("orange")).isTrue();

6.3. Check If a Key-Value Mapping Exists

Similarly, if we want to check whether a map contains a mapping for a specific key and value pair, we can use the containsMapping method:

assertThat(map.containsMapping("fruits","orange")).isTrue();

6.4. Check If a Map Is Empty

To check if a map does not contain any key-value mappings at all, we can use the isEmpty method:

assertThat(map.isEmpty()).isFalse;

6.5. Check the Size of a Map

Finally, we can use the size method to get the total size of the map. When a map has keys with multiple values, then the total size of the map is the count of all the values from all keys:

assertEquals(4, map.size());

7. Implementations

The Apache Commons Collections Library also provides multiple implementations of this interface. Let's have a look at them.

7.1. ArrayListValuedHashMap

An ArrayListValuedHashMap uses an ArrayList internally for storing the values associated with each key, so it allows duplicate key-values pairs:

MultiValuedMap map = new ArrayListValuedHashMap(); map.put("fruits", "apple"); map.put("fruits", "orange"); map.put("fruits", "orange"); assertThat((Collection) map.get("fruits")) .containsExactly("apple", "orange", "orange");

Now, it's worth noting that this class is not thread-safe. Therefore, if we want to use this map from multiple threads, we must be sure to use proper synchronization.

7.2. HashSetValuedHashMap

A HashSetValuedHashMap uses a HashSet for storing the values for each given key. Therefore, it doesn't allow duplicate key-value pairs.

Let's see a quick example, where we add the same key-value mapping twice:

MultiValuedMap map = new HashSetValuedHashMap(); map.put("fruits", "apple"); map.put("fruits", "apple"); assertThat((Collection) map.get("fruits")) .containsExactly("apple");

Notice how, unlike our previous example that used ArrayListValuedHashMap, the HashSetValuedHashMap implementation ignores the duplicate mapping.

The HashSetValuedHashMapclass is also not thread-safe.

7.3. Peta Tidak Boleh DiubahsuaiMultiValuedMap

The UnmodifiableMultiValuedMap adalah kelas penghias yang berguna apabila kita memerlukan contoh tidak berubah daripada MultiValuedMap - iaitu, ia tidak sepatutnya membenarkan pengubahsuaian lebih lanjut:

@Test(expected = UnsupportedOperationException.class) public void givenUnmodifiableMultiValuedMap_whenInserting_thenThrowingException() { MultiValuedMap map = new ArrayListValuedHashMap(); map.put("fruits", "apple"); map.put("fruits", "orange"); MultiValuedMap immutableMap = MultiMapUtils.unmodifiableMultiValuedMap(map); immutableMap.put("fruits", "banana"); // throws exception }

Dan sekali lagi, berbaloi dan berkata bahawa mengubah suai akhir put akan menyebabkan UnsupportedOperationException .

8. Kesimpulannya

Kami telah melihat pelbagai kaedah antara muka MultiValuedMap dari perpustakaan Apache Commons Collections. Di samping itu, kami telah meneroka beberapa pelaksanaan yang popular.

Dan, seperti biasa, kod sumber penuh tersedia di Github.