Code360 powered by Coding Ninjas X Naukri.com. Code360 powered by Coding Ninjas X Naukri.com
Table of contents
1.
Introduction
2.
ConcurrentHashMap
2.1.
Features
2.2.
Constructors
2.3.
Methods/Functions
2.4.
Basic operations
2.5.
Bulk Operations
3.
Frequently Asked Questions
4.
Key Takeaways
Last Updated: Mar 27, 2024

ConcurrentHashMap in Java

Author Yashesvinee V
0 upvote
gp-icon
Data structures & algorithms (Beginner to Intermediate)
Free guided path
13 chapters
99+ problems
gp-badge
Earn badges and level up

Introduction

A HashMap is similar to a HashTable, which maps a key to its value and stores it for future reference. The only difference is that HashMap is not synchronised or thread-safe. For example, if a thread attempts to modify the contents of a HashMap object that is currently being iterated by another thread, it will throw a ConcurrentModificationException. This exception can be avoided by using the ConcurrentHashMap class instead of HashMap.

ConcurrentHashMap supports full concurrency of retrieval and updates despite having the exact functional specifications as HashMap. It implements the ConcurrentMap interface that is capable of synchronising all concurrent activities related to it without affecting the consistency of entries in the map.

Also read, Duck Number in Java and  Hashcode Method in Java

ConcurrentHashMap

Concurrent hash maps can be created by importing :

java.util.concurrent.ConcurrentHashMap

 

Declaration:

public class ConcurrentHashMap<K,​V> extends AbstractMap<K,​V> implements ConcurrentMap<K,​V>, Serializable 

 

K - key object type V - value object type

To create an instance:

ConcurrentHashMap<Key, Value> numbers = new ConcurrentHashMap<>()

Features

  • ConcurrentHashMap is an enhanced version of the HashMap that deals with concurrent thread operations.
     
  • Unlike the HashMap, it is synchronised and does not accept null as a key or value.
     
  • The default concurrency level of a ConcurrenHashMap is 16. This means that a maximum of 16 threads can modify the map contents simultaneously. However, any number of threads can read the map at the same time.
     
  • All objects, by default, can be divided into 16 segments based on the concurrency level. ConcurrentHashMaps implement a Segment/Bucket locking mechanism in which a thread locks a segment in the object it wants to operate on.
     
  • It supports sequential and parallel bulk operations even to maps that are simultaneously modified by multiple threads.

Constructors

Three important parameters are involved with the constructors of this class. 

  • Concurrency level: It specifies the number of threads that would concurrently update the map.
     
  • Load factor: It is a threshold factor used for control resizing.
     
  • Initial capacity: It defines the number of entries the map can hold initially.

 

The ConcurrentHashMap has five constructors:

  • ConcurrentHashMap() -
     
    • It creates a new, empty map with default concurrency level (16), load factor (0.75) and initial capacity (16).
       
ConcurrentHashMap<String, Integer> evenNumbers = new ConcurrentHashMap<>();

 

  • ConcurrentHashMap(int initialCapacity) -

    •  It creates a new, empty map with default concurrency level (16), load factor (0.75) and the specified initial capacity.
       
    • IllegalArgumentException is thrown if the value of initial capacity is negative.
       
ConcurrentHashMap<String, Integer> evenNumbers = new ConcurrentHashMap<>(int initialCapacity);

 

  • ConcurrentHashMap(int initialCapacity, float loadFactor) -

    •  It creates a new, empty map with the default concurrency level (16) and the specified load factor, initial capacity.
       
    • IllegalArgumentException is thrown if the value of initial capacity or load-factor is negative.
       
ConcurrentHashMap<String, Integer> evenNumbers = new ConcurrentHashMap<>((int initialCapacity, float loadFactor);

 

  • ConcurrentHashMap(int initialCapacity, float loadFactor, int concurrencyLevel) -

    •  It creates a new, empty map with the specified concurrency level, load factor and initial capacity.
       
    • IllegalArgumentException is thrown if the value of initial capacity, load factor, or concurrency level is negative.
       
ConcurrentHashMap<String, Integer> evenNumbers = new ConcurrentHashMap<>(int initialCapacity, float loadFactor, int concurrencyLevel);

 

  • ConcurrentHashMap(Map m) - 

    • It creates a new map with the same entries of the given map.
       
ConcurrentHashMap<String, Integer> evenNumbers = new ConcurrentHashMap<>(Map m);


Try it on online java compiler.

Methods/Functions

Method

Type

Description

clear() void It removes all the mappings from a specified map.
compute(K key, remapping function) V Compute a mapping for the specified key and its current value.
computeIfAbsent(K key, mapping function) Computes the value of the specified key using the given remapping function. 
computeIfAbsent(K key, mapping function) Computes a new mapping for the given key and its current value.
contains(Object value)

boolean

 

Checks if a key maps to the specified object value
containsKey(Object Key) It returns true if the given object is a key in the map.
containsValue(Object value) It returns true if the given object is mapped to one or more keys in the map.
elements() Enumeration<V> It returns an enumeration of the values in the map.
keys() Enumeration<K> It returns an enumeration of the keys in the map.
entrySet() Set<Map.Entry<K, V>> It returns a set-view of all the mappings present in the map.
equals(Object o) boolean It returns true if the given object is also a map and has the same object-reference mappings 
merge(K key, V value, remapping function) V It associates a given value with a specified key if it is not mapped.
get(Object key) V It returns the value of the given key if it is present in the map else, it returns null.
getOrDefault(Object key, V defaultValue) V It returns the value of a specific key or a default value if there is no mapping.
hashcode() int It returns the hash code value for the map
isEmpty() boolean It returns true if the map contains no key-value pairs.
keySet() KeySetView<K, V> It returns a set-view of the keys present in the map
put(K key, V value) V It adds a key-value pair to the identity hash map. If the key already exists, then its value is updated.
putIfAbsent(K key, V value) It associates the specified value to a key that is not mapped.
putAll(Map m)  void It copies all the key-value mappings of a given map and replaces the original content of the map
remove(Object key) V It removes the mapping for a given key if it is present in the map.
remove(Object key, Object value) boolean It removes a given key only if it is mapped to the specified value.
size() int It returns the number of key-value pairs in the identity hash map.
mappingCount() long It returns the number of mappings.
toString() String It returns a string representation of the map.
values() Collection<V> It returns a collection view of the values present in the map.
newKeySet() KeySetView<K,boolean> It creates a new set backed by a ConcurrentHashMap to type Boolean.true
replace(K key,V value) V It replaces the value of a given key only if it currently mapped to some value.
replace(K key, V oldValue, V newValue) boolean It replaces the value of a given key only if it is currently mapped to the specified value.
replaceAll(function) void It replaces the values of every key with a value generated by a given function.
reduceEntries(long parallelismThreshold, transformer, reducer)

<U> U

(U - the return type of the transformer)

It gives the accumulation of the given transformations of all entries using a specified reducer to combine values.
reduceEntries(long parallelismThreshold, reducer) Map.Entry<K, V> It gives the accumulation of all entries using a specified reducer to combine values.
  • reduceEntriesToDouble

     
  • reduceEntriesToInt

     
  • reduceEntriesToLong

 

double

It gives the accumulation of the given transformations of all entries using a specified reducer to combine values and the given basis as an identity value.

Parameter: long parallelismThreshold, transformer, data_type basis, reducer

int
long
reduceKeys(long parallelismThreshold, transformer, reducer)

<U> U

(U - the return type of the transformer)

It gives the accumulation of the given transformations of all keys using a specified reducer to combine values.
reduceKeys(long parallelismThreshold, reducer) K It gives the accumulation of all keys using a specified reducer to combine values.
  • reduceKeysToDouble

     
  • reduceKeysToInt

     
  • reduceKeysToLong

 

double

It gives the accumulation of the given transformations of all keys using a specified reducer to combine values and the given basis as an identity value.

Parameter: long parallelismThreshold, transformer, data_type basis, reducer

int
long
reduce(long parallelismThreshold, transformer, reducer)

<U> U

(U - the return type of the transformer)

It gives the accumulation of the given transformations of all key-value pairs using a specified reducer to combine values.
  • reduceToDouble

     
  • reduceToInt

     
  • reduceToLong

 

double

It gives the accumulation of the given transformations of all key-value pairs using a specified reducer to combine values and the given basis as an identity value.

Parameters: long parallelismThreshold, transformer, data_type basis, reducer

int
long
reduceValues(long parallelismThreshold, transformer, reducer)

<U> U

(U - the return type of the transformer)

It gives the accumulation of the given transformations of all values using a specified reducer to combine values.
reduceValues(long parallelismThreshold, reducer) V It gives the accumulation of all values using a specified reducer to combine values.
  • reduceValuesToDouble

     
  • reduceValuesToInt

     
  • reduceValuesToLong

 

double

It gives the accumulation of the given transformations of all values using a specified reducer to combine values and the given basis as an identity value.

Parameter:  long parallelismThreshold, transformer, data_type basis, reducer

int
long
search( long parallelismThreshold, searchFunction)

<U> U

(U - the return type of the search function)

It returns a non-null result from applying the given search function on each (key, value)
searchEntries()

It returns a non-null result from applying the given search function on each entry, key or value.

Parameters: long parallelismThreshold, searchFunction

searchKeys()
searchValues()
forEach(action) void

It performs a given action for each key-value pair.

Optional parameters: long parallelismThreshold, transformer

forEachEntry(action) void

It performs a given action for each entry, key or value.

Optional parameters: long parallelismThreshold, transformer

forEachKey(action)
forEachValue(action)

 

Description of parameters:
 

  • ParallelismThreshold is the estimated number of elements needed for an operation to be executed in parallel.
     
  • Transformer is a function that returns the transformation of an element.
     
  • Basis defines the initial default value for the reducer.
     
  • Reducer is a commutative and associative combining function.

Basic operations

  • Adding elements

    • put(), putAll() and putIfAbsent() methods are used to add elements into the map.
       
import java.util.concurrent.ConcurrentHashMap;
class AddElement 
{
    public static void main(String[] args) 
    {
        ConcurrentHashMap<String, Integer> evenNumbers = new ConcurrentHashMap<>();

        evenNumbers.put("Two", 2);
        evenNumbers.put("Four", 4);

        System.out.println("ConcurrentHashMap of even numbers: " + evenNumbers);

        ConcurrentHashMap<String, Integer> numbers = new ConcurrentHashMap<>();
        numbers.put("One", 1);

        numbers.putAll(evenNumbers);

        numbers.putIfAbsent("Three", 3);
      
        System.out.println("ConcurrentHashMap of numbers: " + numbers);
    }
}

 

Output:

ConcurrentHashMap of even numbers: {Four=4, Two=2}
ConcurrentHashMap of numbers: {One=1, Four=4, Two=2, Three=3}

 

  • Removing elements

    • remove() is used to remove elements from the map.
       
import java.util.concurrent.ConcurrentHashMap;

public class RemoveElement 
{
  public static void main(String[] args) 
  {     
      ConcurrentHashMap<String, Integer> evenNumbers = new ConcurrentHashMap<>();

      evenNumbers.put("One", 1);
      evenNumbers.put("Two", 2);
      evenNumbers.put("Three", 3);
      evenNumbers.put("Four", 4);

      System.out.println("ConcurrentHashMap of numbers: " + evenNumbers);
      
      evenNumbers.remove("One");
      
      // Using remove() on a key-value pair 
      evenNumbers.remove("Three",3);
      
      // Using remove() on a key that has a different value
      evenNumbers.remove("four",2);
    
      System.out.println("ConcurrentHashMap of even numbers: " + evenNumbers);
   }
}


Output:

ConcurrentHashMap of numbers: {One=1, Four=4, Two=2, Three=3}
ConcurrentHashMap of even numbers: {Four=4, Two=2}

 

  • Accessing elements

    • entrySet(), values(), keys(), keySet() and elements() are used to access a set of elements all together.
       
    • get(), getOrDefault() are used to obtain values of specified keys.
       
import java.util.concurrent.ConcurrentHashMap;

public class AccessElement 
{
  public static void main(String[] args) 
  {
      ConcurrentHashMap<String, Integer> numbers = new ConcurrentHashMap<>();

      numbers.put("One", 1);
      numbers.put("Two", 2);
      numbers.put("Three", 3);
      numbers.put("Four", 4);
      
      System.out.println("ConcurrentHashMap Entries: " + numbers.entrySet());
      
      // Using keys() that returns an enumeration object
      Enumeration enum_keys= numbers.keys();
      System.out.print("ConcurrentHashMap Keys: ");
      
      while(enum_keys.hasMoreElements())
        System.out.print(enum_keys.nextElement() + " ");
      System.out.println();
      
      System.out.println("ConcurrentHashMap Values: " + numbers.values());
      
      System.out.println("Value of One is " + numbers.get("One"));
      
      // Using getOrDefault() where default value is set to -1
      System.out.println("Value of Five is " + numbers.getOrDefault("Five",-1));
   }
}


Output:

ConcurrentHashMap Entries: [One=1, Four=4, Two=2, Three=3]
ConcurrentHashMap Keys: One Four Two Three 
ConcurrentHashMap Values: [1, 4, 2, 3]
Value of One is 1
Value of Five is -1

 

  • Traversal - The iterator interface is used to traverse an Identity hash map. The next() method is used to print the consecutive elements of the map.
     
import java.util.concurrent.ConcurrentHashMap;

public class Traverse 
{
  public static void main(String[] args) 
  {
      ConcurrentHashMap<String, Integer> numbers = new ConcurrentHashMap<>();

      numbers.put("One", 1);
      numbers.put("Two", 2);
      numbers.put("Three", 3);
      numbers.put("Four", 4);
      
      // Using entrySet()
      Iterator<ConcurrentHashMap.Entry<String, Integer> >
          itr = numbers.entrySet().iterator();
          
      // The hasNext() method checks if there is a next element
       while (itr.hasNext()) {
          ConcurrentHashMap.Entry<String, Integer> entry = itr.next();
          System.out.println("Key = " + entry.getKey() + ", Value = " + entry.getValue());
      }
   }
}

 

Output:

Key = One, Value = 1
Key = Four, Value = 4
Key = Two, Value = 2
Key = Three, Value = 3


Also see,  Swap Function in Java

Bulk Operations

  • forEach() iterates over entries, keys or values and performs a specific action.
     
public class Main 
{
  public static void main(String[] args) 
  {
      ConcurrentHashMap<String, Integer> numbers = new ConcurrentHashMap<>();

      numbers.put("One", 1);
      numbers.put("Two", 2);
      numbers.put("Three", 3);
      numbers.put("Four", 4);
      
      // forEach() without transformer 
      numbers.forEach(4, (k, v) -> System.out.println("key: " + k + ", value: " + v));

      // forEach() with transformer
      System.out.print("Values are ");
      numbers.forEach(4, (k, v) -> v, (v) -> System.out.print(v + ", "));
   }
}


Output:

key: One, value: 1
key: Two, value: 2
key: Three, value: 3
key: Four, value: 4
Values are 1, 4, 2, 3,

 

  • search() searches the map based on a function and returns the matched entry.
     
public class Main 
{
  public static void main(String[] args) 
  {
      ConcurrentHashMap<String, Integer> numbers = new ConcurrentHashMap<>();

      numbers.put("One", 1);
      numbers.put("Two", 2);
      numbers.put("Three", 3);
      numbers.put("Four", 4);
      
      String key = numbers.search(3, (k, v) -> {return v == 2 ? k: null;});
      System.out.println("Searched value: " + key);
    }
}


Output:

Searched value: Two

 

  • reduce() is used to accumulate each entry, key or value in a map to perform a common task.
     
public class Main 
{
  public static void main(String[] args) 
  {
      ConcurrentHashMap<String, Integer> numbers = new ConcurrentHashMap<>();

      numbers.put("One", 1);
      numbers.put("Two", 2);
      numbers.put("Three", 3);
      numbers.put("Four", 4);
      
      int sum = numbers.reduce(4, (k, v) -> v, (v1, v2) -> v1 + v2);
      System.out.println("Sum of all values: " + sum);
    }
}

 

Output:

Sum of all values: 10
Get the tech career you deserve, faster!
Connect with our expert counsellors to understand how to hack your way to success
User rating 4.7/5
1:1 doubt support
95% placement record
Akash Pal
Senior Software Engineer
326% Hike After Job Bootcamp
Himanshu Gusain
Programmer Analyst
32 LPA After Job Bootcamp
After Job
Bootcamp

Frequently Asked Questions

Q: What are iterators and enumerations?

An iterator is a cursor used to retrieve or remove elements one by one. They are universal and can be applied to any collection object. Iterator objects are created using the iterator() method present in the collection interface.

Enumerations are used to get elements from legacy collections like Vectors, HashTable. Like an iterator, it is a cursor used to read or retrieve elements. However, it cannot remove elements.

Q: What are the differences between ConcurrentHashMap and HashTable?

  • ConcurrentHashMap uses a multiple segment/bucket lock mechanism at the object level, while HashTable uses a single lock for the whole data.
     
  • ConcurrentHashMap uses a fail-safe iterator, and HashTable uses an enumerator to iterate the values of their objects.
     
  • ConcurrentHashMap is faster and has a better performance compared to the HashTable as it experiences synchronisation overhead.

Key Takeaways

The applications and programs built today are expected to have high efficiency and performance while executing concurrent tasks. Maps, hash tables and related interfaces involve multiple threads accessing and modifying their objects concurrently. In such situations, ConcurrentMaps and ConcurrentHashmaps play an essential role. This blog explains the features of ConcurrentHashMaps in detail. It also discusses the various methods provided by this class to perform basic and bulky operations.

Related Links:

Check out the official Coding Ninjas Blog site and visit our Library for more.

Guided path
Free
gridgp-icon
Data structures & algorithms (Beginner to Intermediate)
13 chapters
109+ Problems
gp-badge
Earn badges and level up
Live masterclass