Fix incorrect size calculated by EnumSet.of(varargs) in web mode.
Review by: scottb
git-svn-id: https://google-web-toolkit.googlecode.com/svn/trunk@5876 8db76d5a-ed1c-0410-87a9-c151d255dfc7
diff --git a/user/super/com/google/gwt/emul/java/util/EnumSet.java b/user/super/com/google/gwt/emul/java/util/EnumSet.java
index e0cc934..51c24f1 100644
--- a/user/super/com/google/gwt/emul/java/util/EnumSet.java
+++ b/user/super/com/google/gwt/emul/java/util/EnumSet.java
@@ -229,10 +229,15 @@
E[] all = first.getDeclaringClass().getEnumConstants();
E[] set = Array.createFrom(all);
set[first.ordinal()] = first;
+ int size = 1;
for (E e : rest) {
- set[e.ordinal()] = e;
+ int ordinal = e.ordinal();
+ if (set[ordinal] == null) {
+ set[ordinal] = e;
+ ++size; // count only new elements
+ }
}
- return new EnumSetImpl<E>(all, set, rest.length + 1);
+ return new EnumSetImpl<E>(all, set, size);
}
public static <E extends Enum<E>> EnumSet<E> range(E from, E to) {
diff --git a/user/test/com/google/gwt/emultest/java/util/EnumSetTest.java b/user/test/com/google/gwt/emultest/java/util/EnumSetTest.java
index 07b9104..f709525 100644
--- a/user/test/com/google/gwt/emultest/java/util/EnumSetTest.java
+++ b/user/test/com/google/gwt/emultest/java/util/EnumSetTest.java
@@ -22,6 +22,7 @@
import java.util.List;
import java.util.ArrayList;
import java.util.EnumSet;
+import java.util.NoSuchElementException;
/**
* Tests EnumSet. TODO(tobyr) Consider using Apache collections tests.
@@ -39,6 +40,32 @@
public String getModuleName() {
return "com.google.gwt.emultest.EmulSuite";
}
+
+ /**
+ * Test failure mode from issue 3605. Previously resulted in an incorrect size.
+ */
+ public void testDuplicates() {
+ EnumSet<Numbers> set = EnumSet.of(Numbers.Two, Numbers.One, Numbers.Two, Numbers.One);
+ assertEquals(set.size(), 2);
+ assertTrue(set.contains(Numbers.One));
+ assertTrue(set.contains(Numbers.Two));
+ }
+
+ /**
+ * Test failure mode from issue 3605. Previously resulted in a NoSuchElementException.
+ */
+ public void testDuplicatesToArray() {
+ EnumSet<Numbers> set = EnumSet.of(Numbers.Two, Numbers.One, Numbers.Two, Numbers.One);
+ Numbers[] array = set.toArray(new Numbers[set.size()]);
+ assertNotNull(array);
+ assertEquals(array.length, 2);
+ if (array[0] != Numbers.One && array[1] != Numbers.One) {
+ fail("Numbers.One not found");
+ }
+ if (array[0] != Numbers.Two && array[1] != Numbers.Two) {
+ fail("Numbers.Two not found");
+ }
+ }
public void testNumbers() {
enumTest(Numbers.class);
@@ -77,9 +104,14 @@
assertEquals(numberSet, numbers);
// Attempt to add a duplicate value
+ int numbersSize = numbers.size();
+ int numberSetSize = numberSet.size();
numbers.add(enums[23]);
numberSet.add(enums[23]);
assertEquals(numberSet, numbers);
+ // Check sizes haven't changed
+ assertEquals(numbersSize, numbers.size());
+ assertEquals(numberSetSize, numberSet.size());
numbers = EnumSet.allOf(e);
numberSet.clear();