| Method from org.apache.commons.collections.TestCollection Detail: |
protected boolean areEqualElementsDistinguishable() {
return false;
}
Specifies whether equal elements in the collection are, in fact,
distinguishable with information not readily available. That is, if a
particular value is to be removed from the collection, then there is
one and only one value that can be removed, even if there are other
elements which are equal to it.
In most collection cases, elements are not distinguishable (equal is
equal), thus this method defaults to return false. In some cases,
however, they are. For example, the collection returned from the map's
values() collection view are backed by the map, so while there may be
two values that are equal, their associated keys are not. Since the
keys are distinguishable, the values are.
This flag is used to skip some verifications for iterator.remove()
where it is impossible to perform an equivalent modification on the
confirmed collection because it is not possible to determine which
value in the confirmed collection to actually remove. Tests that
override the default (i.e. where equal elements are distinguishable),
should provide additional tests on iterator.remove() to make sure the
proper elements are removed when remove() is called on the iterator. |
protected Object[] getFullElements() {
ArrayList list = new ArrayList();
list.addAll(Arrays.asList(getFullNonNullElements()));
list.add(4, null);
return list.toArray();
}
Returns an array of objects that are contained in a collection
produced by #makeFullCollection() . Every element in the
returned array must be an element in a full collection.
The default implementation returns a heterogenous array of
objects with some duplicates and with the null element.
Override if you require specific testing elements. Note that if you
override #makeFullCollection() , you must override
this method to reflect the contents of a full collection. |
public static Object[] getFullNonNullElements() {
return new Object[] {
new String(""),
new String("One"),
new Integer(2),
"Three",
new Integer(4),
"One",
new Double(5),
new Float(6),
"Seven",
"Eight",
new String("Nine"),
new Integer(10),
new Short((short)11),
new Long(12),
"Thirteen",
"14",
"15",
new Byte((byte)16)
};
}
Returns a list of elements suitable for return by
getFullElements() . The array returned by this method
does not include null, but does include a variety of objects
of different types. Override getFullElements to return
the results of this method if your collection does not support
the null element. |
public static Object[] getFullNonNullStringElements() {
return new Object[] {
"If","the","dull","substance","of","my","flesh","were","thought",
"Injurious","distance","could","not","stop","my","way",
};
}
Returns a list of string elements suitable for return by
getFullElements() . Override getFullElements to return
the results of this method if your collection does not support
heterogenous elements or the null element. |
protected Object[] getOtherElements() {
return getOtherNonNullElements();
}
Returns an array of elements that are not contained in a
full collection. Every element in the returned array must
not exist in a collection returned by #makeFullCollection() .
The default implementation returns a heterogenous array of elements
without null. Note that some of the tests add these elements
to an empty or full collection, so if your collection restricts
certain kinds of elements, you should override this method. |
public static Object[] getOtherNonNullElements() {
return new Object[] {
new Integer(0),
new Float(0),
new Double(0),
"Zero",
new Short((short)0),
new Byte((byte)0),
new Long(0),
new Character('\u0000"),
"0"
};
}
Returns the default list of objects returned by
getOtherElements() . Includes many objects
of different types. |
public static Object[] getOtherNonNullStringElements() {
return new Object[] {
"For","then","despite",/* of */"space","I","would","be","brought",
"From","limits","far","remote","where","thou","dost","stay"
};
}
Returns a list of string elements suitable for return by
getOtherElements() . Override getOtherElements to return
the results of this method if your collection does not support
heterogenous elements or the null element. |
protected boolean isAddSupported() {
return true;
}
Returns true if the collections produced by
#makeCollection() and #makeFullCollection()
support the add and addAll
operations.
Default implementation returns true. Override if your collection
class does not support add or addAll. |
protected boolean isRemoveSupported() {
return true;
}
Returns true if the collections produced by
#makeCollection() and #makeFullCollection()
support the remove, removeAll,
retainAll, clear and
iterator().remove() methods.
Default implementation returns true. Override if your collection
class does not support removal operations. |
abstract protected Collection makeCollection()
Return a new, empty Collection to be used for testing. |
abstract protected Collection makeConfirmedCollection()
|
abstract protected Collection makeConfirmedFullCollection()
|
protected Collection makeFullCollection() {
Collection c = makeCollection();
c.addAll(Arrays.asList(getFullElements()));
return c;
}
Returns a full collection to be used for testing. The collection
returned by this method should contain every element returned by
#getFullElements() . The default implementation, in fact,
simply invokes addAll on an empty collection with
the results of #getFullElements() . Override this default
if your collection doesn't support addAll. |
public Object makeObject() {
return makeCollection();
}
Returns an empty collection for Object tests. |
protected void resetEmpty() {
this.collection = makeCollection();
this.confirmed = makeConfirmedCollection();
}
Resets the #collection and #confirmed fields to empty
collections. Invoke this method before performing a modification
test. |
protected void resetFull() {
this.collection = makeFullCollection();
this.confirmed = makeConfirmedFullCollection();
}
Resets the #collection and #confirmed fields to full
collections. Invoke this method before performing a modification
test. |
public void testCollectionAdd() {
if (!isAddSupported()) return;
Object[] elements = getFullElements();
for (int i = 0; i < elements.length; i++) {
resetEmpty();
boolean r = collection.add(elements[i]);
confirmed.add(elements[i]);
verify();
assertTrue("Empty collection changed after add", r);
assertTrue("Collection size is 1 after first add",
collection.size() == 1);
}
resetEmpty();
int size = 0;
for (int i = 0; i < elements.length; i++) {
boolean r = collection.add(elements[i]);
confirmed.add(elements[i]);
verify();
if (r) size++;
assertEquals("Collection size should grow after add",
size, collection.size());
assertTrue("Collection should contain added element",
collection.contains(elements[i]));
}
}
|
public void testCollectionAddAll() {
if (!isAddSupported()) return;
resetEmpty();
Object[] elements = getFullElements();
boolean r = collection.addAll(Arrays.asList(elements));
confirmed.addAll(Arrays.asList(elements));
verify();
assertTrue("Empty collection should change after addAll", r);
for (int i = 0; i < elements.length; i++) {
assertTrue("Collection should contain added element",
collection.contains(elements[i]));
}
resetFull();
int size = collection.size();
elements = getOtherElements();
r = collection.addAll(Arrays.asList(elements));
confirmed.addAll(Arrays.asList(elements));
verify();
assertTrue("Full collection should change after addAll", r);
for (int i = 0; i < elements.length; i++) {
assertTrue("Full collection should contain added element",
collection.contains(elements[i]));
}
assertEquals("Size should increase after addAll",
size + elements.length, collection.size());
resetFull();
size = collection.size();
r = collection.addAll(Arrays.asList(getFullElements()));
confirmed.addAll(Arrays.asList(getFullElements()));
verify();
if (r) {
assertTrue("Size should increase if addAll returns true",
size < collection.size());
} else {
assertEquals("Size should not change if addAll returns false",
size, collection.size());
}
}
|
public void testCollectionClear() {
if (!isRemoveSupported()) return;
resetEmpty();
collection.clear(); // just to make sure it doesn't raise anything
verify();
resetFull();
collection.clear();
confirmed.clear();
verify();
}
|
public void testCollectionContains() {
Object[] elements;
resetEmpty();
elements = getFullElements();
for(int i = 0; i < elements.length; i++) {
assertTrue("Empty collection shouldn'y contain element",
!collection.contains(elements[i]));
}
// make sure calls to "contains" don't change anything
verify();
elements = getOtherElements();
for(int i = 0; i < elements.length; i++) {
assertTrue("Empty collection shouldn'y contain element",
!collection.contains(elements[i]));
}
// make sure calls to "contains" don't change anything
verify();
resetFull();
elements = getFullElements();
for(int i = 0; i < elements.length; i++) {
assertTrue("Full collection should contain element.",
collection.contains(elements[i]));
}
// make sure calls to "contains" don't change anything
verify();
resetFull();
elements = getOtherElements();
for(int i = 0; i < elements.length; i++) {
assertTrue("Full collection shouldn't contain element",
!collection.contains(elements[i]));
}
}
|
public void testCollectionContainsAll() {
resetEmpty();
Collection col = new HashSet();
assertTrue("Every Collection should contain all elements of an " +
"empty Collection.", collection.containsAll(col));
col.addAll(Arrays.asList(getOtherElements()));
assertTrue("Empty Collection shouldn't contain all elements of " +
"a non-empty Collection.", !collection.containsAll(col));
// make sure calls to "containsAll" don't change anything
verify();
resetFull();
assertTrue("Full collection shouldn't contain other elements",
!collection.containsAll(col));
col.clear();
col.addAll(Arrays.asList(getFullElements()));
assertTrue("Full collection should containAll full elements",
collection.containsAll(col));
// make sure calls to "containsAll" don't change anything
verify();
col = Arrays.asList(getFullElements()).subList(2, 5);
assertTrue("Full collection should containAll partial full " +
"elements", collection.containsAll(col));
assertTrue("Full collection should containAll itself",
collection.containsAll(collection));
// make sure calls to "containsAll" don't change anything
verify();
col = new ArrayList();
col.addAll(Arrays.asList(getFullElements()));
col.addAll(Arrays.asList(getFullElements()));
assertTrue("Full collection should containAll duplicate full " +
"elements", collection.containsAll(col));
// make sure calls to "containsAll" don't change anything
verify();
}
|
public void testCollectionIsEmpty() {
resetEmpty();
assertEquals("New Collection should be empty.",
true, collection.isEmpty());
// make sure calls to "isEmpty() don't change anything
verify();
resetFull();
assertEquals("Full collection shouldn't be empty",
false, collection.isEmpty());
// make sure calls to "isEmpty() don't change anything
verify();
}
|
public void testCollectionIterator() {
resetEmpty();
Iterator it1 = collection.iterator();
assertEquals("Iterator for empty Collection shouldn't have next.",
false, it1.hasNext());
try {
it1.next();
fail("Iterator at end of Collection should throw " +
"NoSuchElementException when next is called.");
} catch(NoSuchElementException e) {
// expected
}
// make sure nothing has changed after non-modification
verify();
resetFull();
it1 = collection.iterator();
for (int i = 0; i < collection.size(); i++) {
assertTrue("Iterator for full collection should haveNext",
it1.hasNext());
it1.next();
}
assertTrue("Iterator should be finished", !it1.hasNext());
ArrayList list = new ArrayList();
it1 = collection.iterator();
for (int i = 0; i < collection.size(); i++) {
Object next = it1.next();
assertTrue("Collection should contain element returned by " +
"its iterator", collection.contains(next));
list.add(next);
}
try {
it1.next();
fail("iterator.next() should raise NoSuchElementException " +
"after it finishes");
} catch (NoSuchElementException e) {
// expected
}
// make sure nothing has changed after non-modification
verify();
}
|
public void testCollectionIteratorFailFast() {
if (isAddSupported()) {
resetFull();
try {
Iterator iter = collection.iterator();
Object o = getOtherElements()[0];
collection.add(o);
confirmed.add(o);
iter.next();
fail("next after add should raise ConcurrentModification");
} catch (ConcurrentModificationException e) {
// expected
}
verify();
resetFull();
try {
Iterator iter = collection.iterator();
collection.addAll(Arrays.asList(getOtherElements()));
confirmed.addAll(Arrays.asList(getOtherElements()));
iter.next();
fail("next after addAll should raise ConcurrentModification");
} catch (ConcurrentModificationException e) {
// expected
}
verify();
}
if (!isRemoveSupported()) return;
resetFull();
try {
Iterator iter = collection.iterator();
collection.clear();
iter.next();
fail("next after clear should raise ConcurrentModification");
} catch (ConcurrentModificationException e) {
// expected
} catch (NoSuchElementException e) {
// (also legal given spec)
}
resetFull();
try {
Iterator iter = collection.iterator();
collection.remove(getFullElements()[0]);
iter.next();
fail("next after remove should raise ConcurrentModification");
} catch (ConcurrentModificationException e) {
// expected
}
resetFull();
try {
Iterator iter = collection.iterator();
List sublist = Arrays.asList(getFullElements()).subList(2,5);
collection.removeAll(sublist);
iter.next();
fail("next after removeAll should raise ConcurrentModification");
} catch (ConcurrentModificationException e) {
// expected
}
resetFull();
try {
Iterator iter = collection.iterator();
List sublist = Arrays.asList(getFullElements()).subList(2,5);
collection.retainAll(sublist);
iter.next();
fail("next after retainAll should raise ConcurrentModification");
} catch (ConcurrentModificationException e) {
// expected
}
}
Tests that the collection's iterator is fail-fast. |
public void testCollectionIteratorRemove() {
if (!isRemoveSupported()) return;
resetEmpty();
try {
collection.iterator().remove();
fail("New iterator.remove should raise IllegalState");
} catch (IllegalStateException e) {
// expected
}
verify();
try {
Iterator iter = collection.iterator();
iter.hasNext();
iter.remove();
fail("New iterator.remove should raise IllegalState " +
"even after hasNext");
} catch (IllegalStateException e) {
// expected
}
verify();
resetFull();
int size = collection.size();
Iterator iter = collection.iterator();
while (iter.hasNext()) {
Object o = iter.next();
iter.remove();
// if the elements aren't distinguishable, we can just remove a
// matching element from the confirmed collection and verify
// contents are still the same. Otherwise, we don't have the
// ability to distinguish the elements and determine which to
// remove from the confirmed collection (in which case, we don't
// verify because we don't know how).
//
// see areEqualElementsDistinguishable()
if(!areEqualElementsDistinguishable()) {
confirmed.remove(o);
verify();
}
size--;
assertEquals("Collection should shrink by one after " +
"iterator.remove", size, collection.size());
}
assertTrue("Collection should be empty after iterator purge",
collection.isEmpty());
resetFull();
iter = collection.iterator();
iter.next();
iter.remove();
try {
iter.remove();
fail("Second iter.remove should raise IllegalState");
} catch (IllegalStateException e) {
// expected
}
}
|
public void testCollectionRemove() {
if (!isRemoveSupported()) return;
resetEmpty();
Object[] elements = getFullElements();
for (int i = 0; i < elements.length; i++) {
assertTrue("Shouldn't remove nonexistent element",
!collection.remove(elements[i]));
verify();
}
Object[] other = getOtherElements();
resetFull();
for (int i = 0; i < other.length; i++) {
assertTrue("Shouldn't remove nonexistent other element",
!collection.remove(other[i]));
verify();
}
int size = collection.size();
for (int i = 0; i < elements.length; i++) {
resetFull();
assertTrue("Collection should remove extant element",
collection.remove(elements[i]));
// if the elements aren't distinguishable, we can just remove a
// matching element from the confirmed collection and verify
// contents are still the same. Otherwise, we don't have the
// ability to distinguish the elements and determine which to
// remove from the confirmed collection (in which case, we don't
// verify because we don't know how).
//
// see areEqualElementsDistinguishable()
if(!areEqualElementsDistinguishable()) {
confirmed.remove(elements[i]);
verify();
}
assertEquals("Collection should shrink after remove",
size - 1, collection.size());
}
}
|
public void testCollectionRemoveAll() {
if (!isRemoveSupported()) return;
resetEmpty();
assertTrue("Emtpy collection removeAll should return false for " +
"empty input",
!collection.removeAll(Collections.EMPTY_SET));
verify();
assertTrue("Emtpy collection removeAll should return false for " +
"nonempty input",
!collection.removeAll(new ArrayList(collection)));
verify();
resetFull();
assertTrue("Full collection removeAll should return false for " +
"empty input",
!collection.removeAll(Collections.EMPTY_SET));
verify();
assertTrue("Full collection removeAll should return false for " +
"other elements",
!collection.removeAll(Arrays.asList(getOtherElements())));
verify();
assertTrue("Full collection removeAll should return true for " +
"full elements",
collection.removeAll(new HashSet(collection)));
confirmed.removeAll(new HashSet(confirmed));
verify();
resetFull();
int size = collection.size();
Collection all = Arrays.asList(getFullElements()).subList(2, 5);
assertTrue("Full collection removeAll should work",
collection.removeAll(all));
confirmed.removeAll(all);
verify();
assertTrue("Collection should shrink after removeAll",
collection.size() < size);
Iterator iter = all.iterator();
while (iter.hasNext()) {
assertTrue("Collection shouldn't contain removed element",
!collection.contains(iter.next()));
}
}
|
public void testCollectionRetainAll() {
if (!isRemoveSupported()) return;
resetEmpty();
List elements = Arrays.asList(getFullElements());
List other = Arrays.asList(getOtherElements());
assertTrue("Empty retainAll() should return false",
!collection.retainAll(Collections.EMPTY_SET));
verify();
assertTrue("Empty retainAll() should return false",
!collection.retainAll(elements));
verify();
resetFull();
assertTrue("Collection should change from retainAll empty",
collection.retainAll(Collections.EMPTY_SET));
confirmed.retainAll(Collections.EMPTY_SET);
verify();
resetFull();
assertTrue("Collection changed from retainAll other",
collection.retainAll(other));
confirmed.retainAll(other);
verify();
resetFull();
int size = collection.size();
assertTrue("Collection shouldn't change from retainAll elements",
!collection.retainAll(elements));
verify();
assertEquals("Collection size shouldn't change", size,
collection.size());
resetFull();
size = collection.size();
assertTrue("Collection should changed by partial retainAll",
collection.retainAll(elements.subList(2, 5)));
confirmed.retainAll(elements.subList(2, 5));
verify();
Iterator iter = collection.iterator();
while (iter.hasNext()) {
assertTrue("Collection only contains retained element",
elements.subList(2, 5).contains(iter.next()));
}
resetFull();
HashSet set = new HashSet(elements);
size = collection.size();
assertTrue("Collection shouldn't change from retainAll without " +
"duplicate elements", !collection.retainAll(set));
verify();
assertEquals("Collection size didn't change from nonduplicate " +
"retainAll", size, collection.size());
}
|
public void testCollectionSize() {
resetEmpty();
assertEquals("Size of new Collection is 0.", 0, collection.size());
resetFull();
assertTrue("Size of full collection should be greater than zero",
collection.size() > 0);
}
|
public void testCollectionToArray() {
resetEmpty();
assertEquals("Empty Collection should return empty array for toArray",
0, collection.toArray().length);
resetFull();
Object[] array = collection.toArray();
assertEquals("Full collection toArray should be same size as " +
"collection", array.length, collection.size());
Object[] confirmedArray = confirmed.toArray();
assertEquals("length of array from confirmed collection should " +
"match the length of the collection's array",
confirmedArray.length, array.length);
boolean[] matched = new boolean[array.length];
for (int i = 0; i < array.length; i++) {
assertTrue("Collection should contain element in toArray",
collection.contains(array[i]));
boolean match = false;
// find a match in the confirmed array
for(int j = 0; j < array.length; j++) {
// skip already matched
if(matched[j]) continue;
if(array[i] == confirmedArray[j] ||
(array[i] != null && array[i].equals(confirmedArray[j]))) {
matched[j] = true;
match = true;
break;
}
}
if(!match) {
fail("element " + i + " in returned array should be found " +
"in the confirmed collection's array");
}
}
for(int i = 0; i < matched.length; i++) {
assertEquals("Collection should return all its elements in " +
"toArray", true, matched[i]);
}
}
|
public void testCollectionToArray2() {
resetEmpty();
Object[] a = new Object[] { new Object(), null, null };
Object[] array = collection.toArray(a);
assertEquals("Given array shouldn't shrink", array, a);
assertEquals("Last element should be set to null", a[0], null);
verify();
resetFull();
try {
array = collection.toArray(new Void[0]);
fail("toArray(new Void[0]) should raise ArrayStore");
} catch (ArrayStoreException e) {
// expected
}
verify();
try {
array = collection.toArray(null);
fail("toArray(null) should raise NPE");
} catch (NullPointerException e) {
// expected
}
verify();
array = collection.toArray(new Object[0]);
a = collection.toArray();
assertEquals("toArrays should be equal",
Arrays.asList(array), Arrays.asList(a));
// Figure out if they're all the same class
// TODO: It'd be nicer to detect a common superclass
HashSet classes = new HashSet();
for (int i = 0; i < array.length; i++) {
classes.add((array[i] == null) ? null : array[i].getClass());
}
if (classes.size() > 1) return;
Class cl = (Class)classes.iterator().next();
a = (Object[])Array.newInstance(cl, 0);
array = collection.toArray(a);
assertEquals("toArray(Object[]) should return correct array type",
a.getClass(), array.getClass());
assertEquals("type-specific toArrays should be equal",
Arrays.asList(array),
Arrays.asList(collection.toArray()));
verify();
}
|
public void testCollectionToString() {
resetEmpty();
assertTrue("toString shouldn't return null",
collection.toString() != null);
resetFull();
assertTrue("toString shouldn't return null",
collection.toString() != null);
}
Tests toString on a collection. |
public void testUnsupportedAdd() {
if (isAddSupported()) return;
resetEmpty();
try {
collection.add(new Object());
fail("Emtpy collection should not support add.");
} catch (UnsupportedOperationException e) {
// expected
}
// make sure things didn't change even if the expected exception was
// thrown.
verify();
try {
collection.addAll(Arrays.asList(getFullElements()));
fail("Emtpy collection should not support addAll.");
} catch (UnsupportedOperationException e) {
// expected
}
// make sure things didn't change even if the expected exception was
// thrown.
verify();
resetFull();
try {
collection.add(new Object());
fail("Full collection should not support add.");
} catch (UnsupportedOperationException e) {
// expected
}
// make sure things didn't change even if the expected exception was
// thrown.
verify();
try {
collection.addAll(Arrays.asList(getOtherElements()));
fail("Full collection should not support addAll.");
} catch (UnsupportedOperationException e) {
// expected
}
// make sure things didn't change even if the expected exception was
// thrown.
verify();
}
If #isAddSupported() returns false, tests that add operations
raise UnsupportedOperationException. |
public void testUnsupportedRemove() {
if (isRemoveSupported()) return;
resetEmpty();
try {
collection.clear();
fail("clear should raise UnsupportedOperationException");
} catch (UnsupportedOperationException e) {
// expected
}
verify();
try {
collection.remove(null);
fail("remove should raise UnsupportedOperationException");
} catch (UnsupportedOperationException e) {
// expected
}
verify();
try {
collection.removeAll(null);
fail("removeAll should raise UnsupportedOperationException");
} catch (UnsupportedOperationException e) {
// expected
}
verify();
try {
collection.retainAll(null);
fail("removeAll should raise UnsupportedOperationException");
} catch (UnsupportedOperationException e) {
// expected
}
verify();
resetFull();
try {
Iterator iterator = collection.iterator();
iterator.next();
iterator.remove();
fail("iterator.remove should raise UnsupportedOperationException");
} catch (UnsupportedOperationException e) {
// expected
}
verify();
}
If isRemoveSupported() returns false, tests to see that remove
operations raise an UnsupportedOperationException. |
protected void verify() {
int confirmedSize = confirmed.size();
assertEquals("Collection size should match confirmed collection's",
confirmedSize, collection.size());
assertEquals("Collection isEmpty() result should match confirmed " +
" collection's",
confirmed.isEmpty(), collection.isEmpty());
// verify the collections are the same by attempting to match each
// object in the collection and confirmed collection. To account for
// duplicates and differing orders, each confirmed element is copied
// into an array and a flag is maintained for each element to determine
// whether it has been matched once and only once. If all elements in
// the confirmed collection are matched once and only once and there
// aren't any elements left to be matched in the collection,
// verification is a success.
// copy each collection value into an array
Object[] confirmedValues = new Object[confirmedSize];
Iterator iter;
iter = confirmed.iterator();
int pos = 0;
while(iter.hasNext()) {
confirmedValues[pos++] = iter.next();
}
// allocate an array of boolean flags for tracking values that have
// been matched once and only once.
boolean[] matched = new boolean[confirmedSize];
// now iterate through the values of the collection and try to match
// the value with one in the confirmed array.
iter = collection.iterator();
while(iter.hasNext()) {
Object o = iter.next();
boolean match = false;
for(int i = 0; i < confirmedSize; i++) {
if(matched[i]) {
// skip values already matched
continue;
}
if(o == confirmedValues[i] ||
(o != null && o.equals(confirmedValues[i]))) {
// values matched
matched[i] = true;
match = true;
break;
}
}
// no match found!
if(!match) {
fail("Collection should not contain a value that the " +
"confirmed collection does not have.");
}
}
// make sure there aren't any unmatched values
for(int i = 0; i < confirmedSize; i++) {
if(!matched[i]) {
// the collection didn't match all the confirmed values
fail("Collection should contain all values that are in the " +
"confirmed collection");
}
}
}
|