Polb Polb - 16 days ago 6
Java Question

HashSet addAll method modifies class internal field

I have a class which extends a parametrized version of HashSet. This class has an internal field

currentSize
which keeps track of how many elements have been added so far. The child class overrides the base class'
add
and
addAll
methods so the
currentSize
increases accordingly. My problem is that inside
addAll
, the size of the set is added two times to the
currentSize
counter, not once. Below is my class' code:

public class InheritHashSet extends HashSet<Integer> {
private int currentSize = 0;

@Override
public boolean add(Integer e) {
currentSize++;
super.add(e);
}

@Override
public boolean addAll(Collection<? extends Integer> e) {
currentSize += e.size();
super.addAll(e);
}

public int getCurrentSize() {
return currentSize;
}
}


The
add
method seems to be working fine, since after adding three elements,
currentSize
is 3, but the following will add 6 to the
currentSize
instead of 3:

InheritHashSet ihs = new InheritHashSet();
Collection<Integer> c = new LinkedList<Integer>();
c.add(new Integer(0));
c.add(new Integer(1));
c.add(new Integer(2));
ihs.addAll(c);
System.out.println(ihs.getCurrentSize()); // prints 6 instead of 3


It looks like the call to
super.addAll(e)
also modifies the
currentSize
(this does not seem to make any sense at all).

Answer

The addAll() method of the InheritHashSet class first set currentSize = 3, with currentSize += e.size(); instruction. Then super.addAll(e); calls add(e) method three times. For dynamic binding the public boolean add(Integer e) of class InheritHashSet is invoked first and then currentSize is then incremented to 6.

for this reason you should implement addAll method in this way:

@Override
public boolean addAll(Collection<? extends Integer> e) {
    return super.addAll(e);
}