What is the use of adding a null key or value to a HashMap in Java?
Solution 1
I'm not positive what you're asking, but if you're looking for an example of when one would want to use a null key, I use them often in maps to represent the default case (i.e. the value that should be used if a given key isn't present):
Map<A, B> foo;
A search;
B val = foo.containsKey(search) ? foo.get(search) : foo.get(null);
HashMap
handles null keys specially (since it can't call .hashCode()
on a null object), but null values aren't anything special, they're stored in the map like anything else
Solution 2
One example would be for modeling trees. If you are using a HashMap to represent a tree structure, where the key is the parent and the value is list of children, then the values for the null
key would be the root nodes.
Solution 3
One example of usage for null
values is when using a HashMap
as a cache for results of an expensive operation (such as a call to an external web service) which may return null
.
Putting a null
value in the map then allows you to distinguish between the case where the operation has not been performed for a given key (cache.containsKey(someKey)
returns false
), and where the operation has been performed but returned a null
value (cache.containsKey(someKey)
returns true
, cache.get(someKey)
returns null
).
Without null
values, you would have to either put some special value in the cache to indicate a null
response, or simply not cache that response at all and perform the operation every time.
Solution 4
The answers so far only consider the worth of have a null
key, but the question also asks about any number of null values
.
The benefit of storing the value null
against a key in a HashMap is the same as in databases, etc - you can record a distinction between having a value that is empty (e.g. string ""), and not having a value at all (null).
Solution 5
Here's my only-somewhat-contrived example of a case where the null
key can be useful:
public class Timer {
private static final Logger LOG = Logger.getLogger(Timer.class);
private static final Map<String, Long> START_TIMES = new HashMap<String, Long>();
public static synchronized void start() {
long now = System.currentTimeMillis();
if (START_TIMES.containsKey(null)) {
LOG.warn("Anonymous timer was started twice without being stopped; previous timer has run for " + (now - START_TIMES.get(null).longValue()) +"ms");
}
START_TIMES.put(null, now);
}
public static synchronized long stop() {
if (! START_TIMES.containsKey(null)) {
return 0;
}
return printTimer("Anonymous", START_TIMES.remove(null), System.currentTimeMillis());
}
public static synchronized void start(String name) {
long now = System.currentTimeMillis();
if (START_TIMES.containsKey(name)) {
LOG.warn(name + " timer was started twice without being stopped; previous timer has run for " + (now - START_TIMES.get(name).longValue()) +"ms");
}
START_TIMES.put(name, now);
}
public static synchronized long stop(String name) {
if (! START_TIMES.containsKey(name)) {
return 0;
}
return printTimer(name, START_TIMES.remove(name), System.currentTimeMillis());
}
private static long printTimer(String name, long start, long end) {
LOG.info(name + " timer ran for " + (end - start) + "ms");
return end - start;
}
}
subhashis
Updated on July 08, 2022Comments
-
subhashis almost 2 years
HashMap allows one null key and any number of null values. What is the use of it?
-
Pacerier about 12 yearsSo if .hashCode() is not possible on null who decides which carriage the null key will enter?
-
Michael Mrozek about 12 years@Pacerier There's a special method in
HashMap
(putForNullKey
) that handles it; it stores it in table 0 -
Nic over 8 yearsIf you're trying to stop a nonexistent timer, or one that's been stopped already, that should be an error, not ignored.
-
aroth over 8 years@QPaysTaxes - Depends on your intent. If you want a lightweight utility that can be easily used, you generally don't want to
throw Exception
's around. Besides, it's not like attempting to stop a non-existent or already-stopped timer is something that the caller can generally recover from. -
dheerajraaj almost 7 years@MichaelMrozek your last line
B val = foo.containsKey(search) ? foo.get(search) : foo.get(null);
I think we can simply call get method on search key which will have same result.B val = foo.get(search);
could you please correct me if I am getting something wrong? -
Michael Mrozek almost 7 years@dheeraj92 Your code will set
val
tonull
if the key doesn't exist; mine sets it to whatevernull
maps to in the map. That was the point, I store a default non-null value at thenull
key in the map and use it if the actual key doesn't exist