Explore Courses Blog Tutorials Interview Questions
0 votes
1 view
in Java by (10.2k points)

I was surprised by the fact that Map<?,?> is not a Collection<?>.

I thought it'd make a LOT of sense if it was declared as such:

public interface Map<K,V> extends Collection<Map.Entry<K,V>>

After all, a Map<K,V> is a collection of Map.Entry<K,V>, isn't it?

So is there a good reason why it's not implemented as such?

Thanks to Cletus for a most authoritative answer, but I'm still wondering why, if you can already view a Map<K,V> as Set<Map.Entries<K,V>> (via entrySet()), it doesn't just extend that interface instead.

If a Map is a Collection, what are the elements? The only reasonable answer is "Key-value pairs"

Exactly, interface Map<K,V> extends Set<Map.Entry<K,V>> would be great!

but this provides a very limited (and not particularly useful) Map abstraction.

But if that's the case then why is entrySet specified by the interface? It must be useful somehow (and I think it's easy to argue for that position!).

You can't ask what value a given key maps to, nor can you delete the entry for a given key without knowing what value it maps to.

I'm not saying that that's all there is to it to Map! It can and should keep all the other methods (except entrySet, which is redundant now)!

1 Answer

0 votes
by (46k points)

While you've gotten a number of answers that cover your question fairly directly, I think it might be useful to step back a bit, and look at the question a bit more generally. That is, not to look specifically at how the Java library happens to be written, and look at why it's written that way.

The problem here is that inheritance only models one type of commonality. If you pick out two things that both seem "collection-like", you can probably pick out a 8 or 10 things they have in common. If you pick out a different pair of "collection-like" things, they'll also 8 or 10 things in common -- but they won't be the same 8 or 10 things as the first pair.

If you look at a dozen or so different "collection-like" things, virtually every one of them will probably have something like 8 or 10 characteristics in common with at least one other one -- but if you look at what's shared across every one of them, you're left with practically nothing.

This is a situation that inheritance (especially single inheritance) just doesn't model well. There's no clean dividing line between which of those are really collections and which aren't -- but if you want to define a meaningful Collection class, you're stuck with leaving some of them out. If you leave only a few of them out, your Collection class will only be able to provide quite a sparse interface. If you leave more out, you'll be able to give it a richer interface.

Some also take the option of basically saying: "this type of collection supports operation X, but you're not allowed to use it, by deriving from a base class that defines X, but attempting to use the derived class' X fails (e.g., by throwing an exception).

That still leaves one problem: almost regardless of which you leave out and which you put in, you're going to have to draw a hard line between what classes are in and what are out. No matter where you draw that line, you're going to be left with a clear, rather artificial, division between some things that are quite similar.

Related questions

0 votes
1 answer
0 votes
1 answer
asked Nov 13, 2019 in Java by Nigam (4k points)
0 votes
1 answer
asked Aug 26, 2019 in Java by Krishna (2.6k points)
0 votes
1 answer
asked Aug 13, 2019 in Java by Nigam (4k points)

Browse Categories