Java hashmap initialization in one line

Initialize Map with Values in Java

In this tutorial, we’ll learn different ways to initialize a Map with values in Java.

Using Map.of() and Map.ofEntries()

It is possible to initialize a Map with values in a single expression if you are using Java 9 or higher version using Map.of() and Map.ofEntries() method. This is shortest possible way so far.

Map.of()

Java 9 provides mutiple Map.of() overloaded methods to initialize a Map with upto 10 key-value pairs.

MapString, Integer> emptyMap = Map.of(); MapString, Integer> singletonMap = Map.of("A", 1); MapString, Integer> map = Map.of("A", 1, "B", 2, "C", 3); 
Map.ofEntries()

If you have more than 10 key-value pairs to initialize, then you should use Map.ofEntries() method. This method has no limit and you can define any number of key-value pairs.

MapString, Integer> map = Map.ofEntries(  Map.entry("A", 1),  Map.entry("B", 2),  Map.entry("C", 3),  Map.entry("D", 4),  Map.entry("E", 5),  Map.entry("F", 6),  Map.entry("G", 7),  Map.entry("H", 8),  Map.entry("I", 9),  Map.entry("J", 10),  Map.entry("K", 11),  Map.entry("L", 12) );  map.put("M", 13); // Throw UnsupportedOperationException  map.remove("A"); // Throw UnsupportedOperationException 
Mutable Map

Thing to note that both Map.of() and Map.ofEntries() return an immutable map which means that adding or removing an element in Map result into java.lang.UnsupportedOperationException exception.

You can avoid this by creating a mutable map (by copying the immutable map to new HashMap ) in this way:-

MapString, Integer> mutableEmptyMap = new HashMap<>(Map.of()); MapString, Integer> mutableSingletonMap = new HashMap<>(Map.of("A", 1)); MapString, Integer> mutableMap = new HashMap<>(Map.ofEntries(  Map.entry("A", 1),  Map.entry("B", 2),  Map.entry("C", 3),  Map.entry("D", 4),  Map.entry("E", 5),  Map.entry("F", 6),  Map.entry("G", 7),  Map.entry("H", 8),  Map.entry("I", 9),  Map.entry("J", 10),  Map.entry("K", 11),  Map.entry("L", 12) ));  mutableMap.put("M", 13); // It works!  mutableMap.remove("A"); // It works! 

Using Java Collections

Java Collections class provide methods to initialize emptyMap() , singletonMap() and unmodifiableMap() . Note that all these methods return immutable map

MapString, Integer> emptyMap = Collections.emptyMap(); MapString, Integer> singletonMap = Collections.singletonMap("A", 1);  singletonMap.put("B", 2); // Throw UnsupportedOperationException  singletonMap.remove("A"); // Throw UnsupportedOperationException  MapString, Integer> mutableMap = new HashMap<>(singletonMap); mutableMap.put("B", 2); // It works!  MapString, Integer> immutableMap = Collections.unmodifiableMap(mutableMap); immutableMap.put("B", 2); // Throw UnsupportedOperationException 

Initialize Map as an instance variable

If you initialize a Map as an instance variable, keep the initialization in a constructor or instance initializer:-

public class MyClass    MapString, Integer> instanceMap = new HashMap<>();    instanceMap.put("A", 1);  instanceMap.put("B", 2);  > > 

Initialize Map as a static variable

If you initialize a Map as a static class variable, keep the initialization in a static initializer:-

public class MyClass    static MapString, Integer> staticMap = new HashMap<>();  static  staticMap.put("A", 1);  staticMap.put("B", 2);  > > 

Using Double Brace Initialization

You can initialize map with values using Double Brace Initialization:-

MapString, Integer> map = new HashMap<>()  < put("A", 1);  put("B", 2); >>; 

In Double brace initialization > , first brace creates a new Anonymous Inner Class, the second brace declares an instance initializer block that is run when the anonymous inner class is instantiated.

This approach is not recommended as it creates an extra class at each usage. It also holds hidden references to the enclosing instance and any captured objects. This may cause memory leaks or problems with serialization.

The alternative approach for this is to create a function to initialize a map:-

// It works for all Java versions, mutable map.  MapString, Integer> map = createMap(); map.put("C", "3"); // It works!  private static MapString, String> createMap()   MapString, Integer> map = new HashMap<>();  map.put("A", 1);  map.put("B", 2);  return map; > 

Using Stream Collectors.toMap()

We can also use Java 8 Stream API to initialize a Map with values.

When both key and value are of same type (e.g. String):-

MapString, String> mutableMap1 = Stream.of(new String[][]  "A", "a">,  "B", "b">,  "C", "c"> >).collect(Collectors.toMap(p -> p[0], p -> p[1])); 

When both key and value are of different type (e.g. String and Integer):-

MapString, Integer> mutableMap2 = Stream.of(new Object[][]  "A", 1>,  "B", 2>,  "C", 3> >).collect(Collectors.toMap(p -> (String) p[0], p -> (Integer) p[1])); 

Another approach that can easily accommodate different types for key and value involves creating a stream of map entries.

MapString, Integer> mutableMap3 = Stream.of(  new AbstractMap.SimpleEntry<>("A", 1),  new AbstractMap.SimpleEntry<>("B", 2),  new AbstractMap.SimpleEntry<>("C", 3))  .collect(Collectors.toMap(Map.Entry::getKey, Map.Entry::getValue));  MapString, Integer> mutableMap4 = Stream.of(  new AbstractMap.SimpleImmutableEntry<>("A", 1),  new AbstractMap.SimpleImmutableEntry<>("B", 2),  new AbstractMap.SimpleImmutableEntry<>("C", 3))  .collect(Collectors.toMap(Map.Entry::getKey, Map.Entry::getValue)); 

The only difference between SimpleEntry and SimpleImmutableEntry is that you can set the value of SimpleEntry instance once initialized whereas set value of SimpleImmutableEntry after initialization throw UnsupportedOperationException .

Note that all the maps we have initialized using streams so far are mutable map means we can add or remove elements from them. You can initialize an immutable map using streams in this way:-

 MapString, Integer> map5 = Stream.of(  new AbstractMap.SimpleEntry<>("A", 1),  new AbstractMap.SimpleEntry<>("B", 2),  new AbstractMap.SimpleEntry<>("C", 3))  .collect(Collectors.collectingAndThen(  Collectors.toMap(Map.Entry::getKey, Map.Entry::getValue),  Collections::unmodifiableMap  )); 

Conclusion

Let’s look at the summary of all the ways to initialize a Map with values:-

  1. Using Map.of() and Map.ofEntries() – Recommended this single line expression if you use Java 9 and above
  2. Using Java Collections – Works with all Java versions. Useful to define singleton map upto Java 8
  3. Using Double Brace Initialization — Avoid Double braces initialization. Create a method instead.
  4. Initialize Map as an instance variable — Recommended to initialize instance variable
  5. Initialize Map as a static variable — Recommended to initialize static variable
  6. Using Stream Collectors.toMap() – Too many lines of code. We can use other alternatives if possible to avoid boilerplate code.

See Also

Ashish Lahoti avatar

Ashish Lahoti is a Software Engineer with 12+ years of experience in designing and developing distributed and scalable enterprise applications using modern practices. He is a technology enthusiast and has a passion for coding & blogging.

Источник

How to initialize HashMap with values in Java? Example

There is often a situation where you would like to create a HashMap with some pre-defined mapping, but unfortunately, Java doesn’t provide map literals like Groovy or Scala to create the map with values in the same line. If you remember, we have faced the same issue with other Collection classes as well e.g. ArrayList, Vector, or LinkedList. But ArrayList is lucky because you can still use the Arrays.asList() method to create and initialize the ArrayList in just one line as shown here. But, how do you initialize the HashMap with values in Java?

There is no such method like Arrays.asMap() or Collections.asMap() , and this is not just the question about HashMap but also about Hashtable, LinkedHashMap and ConcurrentHashMap.

Well, there is an idiom called double brace initialization, which you can use to initialize the HashMap at the time of declaration. I’ll show you how to use that double brace initialization to create HashMap with values in this article with a simple example.

How to create HashMap with values in Java

As I told you can use the Double brace initialization to create HashMap with values. Btw, this is not a very good pattern, in fact, it is considered as an anti-pattern in Java, but if you are doing this just for utility or testing purposes then it’s ok.

This idiom internally uses the instance initializer of Anonymous inner class and costs an extra class every time you use it, but you can use it to initialize both static and non-static HashMap as shown in our example.

Another drawback of this idiom is that it holds a hidden reference of enclosing class which may cause the memory leak in Java application.

How to create HashMap with values in Java

The good thing about this idiom is that It requires less code i.e. you don’t need to create HashMap without values and then subsequently call the put() method, but you can both create and initialize the Map in the same line.

You can also use double brace initialization with LinkedHashMap , TreeMap , ConcurrentHashMap, and Hashtable , in fact, with any Map implementation e.g. EnumMap and WeakHashMAp.

Java Program to create HashMap with values

Here is our sample Java program to create and initialize the HashMap in the same line. In this example, we have used the double brace initialization idiom to initialize both static and non-static HashMap.

If you look at our program, you will find that we have a map called squares which are supposed to contain the number and its square.

This HashMap is initialized in the static initializer block. Then, we have another Integer to String Map called IdToName , this is also created and initialized at the same line.

import java.util.HashMap; import java.util.Map; /** * Java Program to show you can initialize a HashMap wit values in one line. * You can use this technique to initialize static Maps in Java. * * @author WINDOWS 8 */ public class HashMapWithValues < private static final Map squares; static< squares = new HashMap () >; > public static void main(String args[]) < Map idToName = new HashMap () "John"); put(102, "John"); put(103, "John"); >>; System.out.println(idToName); System.out.println(squares); > > Output : =John, 102=John, 103=John> =4, 3=9, 4=16>

Pros and Cons

Though this technique, double brace initialization looks great when you first learn about it, it has its shares of problems as discussed in the second paragraph. Let’s see the advantages and disadvantages of the double brace initialization pattern for quick reference:

Advantages:
1) less line of code
2) Instantiation and initialization in the same expression.

Disadvantages:
1) Not very readable. This idiom internally uses the Anonymous inner class, which is not clear by just looking at it.
2) It creates a new class every time you use this pattern to initialize HashMap.
3) It holds a hidden reference of the enclosing instance, which may cause the memory leak in the Java application.

That’s all about how to initialize HashMap in Java in one line. You can use the double brace initialization pattern to create HashMap with values but beware of all the disadvantages associated with this idiom. It’s good for testing and demo purposes but I don’t advise you to use this technique in production. Instead, load data from the database or config file.

  • The difference between HashMap and LinkedHashMap in Java? (answer)
  • The best way to iterate over HashMap in Java? (answer)
  • How to sort the HashMap on keys and values in Java? (solution)
  • 3 ways to loop over a Map in Java? (example)
  • The difference between HashMap and ConcurrentHashMap in Java? (answer)

Источник

Читайте также:  Reset css text css
Оцените статью