CollectionRetainAllTester.java revision 7dd252788645e940eada959bdde927426e2531c9
1/* 2 * Copyright (C) 2008 The Guava Authors 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17package com.google.common.collect.testing.testers; 18 19import static com.google.common.collect.testing.features.CollectionFeature.ALLOWS_NULL_VALUES; 20import static com.google.common.collect.testing.features.CollectionFeature.SUPPORTS_REMOVE; 21import static com.google.common.collect.testing.features.CollectionSize.ONE; 22import static com.google.common.collect.testing.features.CollectionSize.ZERO; 23 24import com.google.common.annotations.GwtCompatible; 25import com.google.common.collect.testing.AbstractCollectionTester; 26import com.google.common.collect.testing.MinimalCollection; 27import com.google.common.collect.testing.features.CollectionFeature; 28import com.google.common.collect.testing.features.CollectionSize; 29 30import java.util.Arrays; 31import java.util.Collection; 32import java.util.Collections; 33import java.util.List; 34 35/** 36 * A generic JUnit test which tests {@code retainAll} operations on a 37 * collection. Can't be invoked directly; please see 38 * {@link com.google.common.collect.testing.CollectionTestSuiteBuilder}. 39 * 40 * <p>This class is GWT compatible. 41 * 42 * @author Chris Povirk 43 */ 44@SuppressWarnings("unchecked") // too many "unchecked generic array creations" 45@GwtCompatible 46public class CollectionRetainAllTester<E> extends AbstractCollectionTester<E> { 47 48 /** 49 * A collection of elements to retain, along with a description for use in 50 * failure messages. 51 */ 52 private class Target { 53 private final Collection<E> toRetain; 54 private final String description; 55 56 private Target(Collection<E> toRetain, String description) { 57 this.toRetain = toRetain; 58 this.description = description; 59 } 60 61 @Override public String toString() { 62 return description; 63 } 64 } 65 66 private Target empty; 67 private Target disjoint; 68 private Target superset; 69 private Target nonEmptyProperSubset; 70 private Target sameElements; 71 private Target partialOverlap; 72 private Target containsDuplicates; 73 private Target nullSingleton; 74 75 @Override public void setUp() throws Exception { 76 super.setUp(); 77 78 empty = new Target(emptyCollection(), "empty"); 79 /* 80 * We test that nullSingleton.retainAll(disjointList) does NOT throw a 81 * NullPointerException when disjointList does not, so we can't use 82 * MinimalCollection, which throws NullPointerException on calls to 83 * contains(null). 84 */ 85 List<E> disjointList = Arrays.asList(samples.e3, samples.e4); 86 disjoint 87 = new Target(disjointList, "disjoint"); 88 superset 89 = new Target(MinimalCollection.of( 90 samples.e0, samples.e1, samples.e2, samples.e3, samples.e4), 91 "superset"); 92 nonEmptyProperSubset 93 = new Target(MinimalCollection.of(samples.e1), "subset"); 94 sameElements 95 = new Target(Arrays.asList(createSamplesArray()), "sameElements"); 96 containsDuplicates = new Target( 97 MinimalCollection.of(samples.e0, samples.e0, samples.e3, samples.e3), 98 "containsDuplicates"); 99 partialOverlap 100 = new Target(MinimalCollection.of(samples.e2, samples.e3), 101 "partialOverlap"); 102 nullSingleton 103 = new Target(Collections.<E>singleton(null), "nullSingleton"); 104 } 105 106 // retainAll(empty) 107 108 @CollectionFeature.Require(SUPPORTS_REMOVE) 109 @CollectionSize.Require(ZERO) 110 public void testRetainAll_emptyPreviouslyEmpty() { 111 expectReturnsFalse(empty); 112 expectUnchanged(); 113 } 114 115 @CollectionFeature.Require(absent = SUPPORTS_REMOVE) 116 @CollectionSize.Require(ZERO) 117 public void testRetainAll_emptyPreviouslyEmptyUnsupported() { 118 expectReturnsFalseOrThrows(empty); 119 expectUnchanged(); 120 } 121 122 @CollectionFeature.Require(SUPPORTS_REMOVE) 123 @CollectionSize.Require(absent = ZERO) 124 public void testRetainAll_emptyPreviouslyNonEmpty() { 125 expectReturnsTrue(empty); 126 expectContents(); 127 expectMissing(samples.e0, samples.e1, samples.e2); 128 } 129 130 @CollectionFeature.Require(absent = SUPPORTS_REMOVE) 131 @CollectionSize.Require(absent = ZERO) 132 public void testRetainAll_emptyPreviouslyNonEmptyUnsupported() { 133 expectThrows(empty); 134 expectUnchanged(); 135 } 136 137 // retainAll(disjoint) 138 139 @CollectionFeature.Require(SUPPORTS_REMOVE) 140 @CollectionSize.Require(ZERO) 141 public void testRetainAll_disjointPreviouslyEmpty() { 142 expectReturnsFalse(disjoint); 143 expectUnchanged(); 144 } 145 146 @CollectionFeature.Require(absent = SUPPORTS_REMOVE) 147 @CollectionSize.Require(ZERO) 148 public void testRetainAll_disjointPreviouslyEmptyUnsupported() { 149 expectReturnsFalseOrThrows(disjoint); 150 expectUnchanged(); 151 } 152 153 @CollectionFeature.Require(SUPPORTS_REMOVE) 154 @CollectionSize.Require(absent = ZERO) 155 public void testRetainAll_disjointPreviouslyNonEmpty() { 156 expectReturnsTrue(disjoint); 157 expectContents(); 158 expectMissing(samples.e0, samples.e1, samples.e2); 159 } 160 161 @CollectionFeature.Require(absent = SUPPORTS_REMOVE) 162 @CollectionSize.Require(absent = ZERO) 163 public void testRetainAll_disjointPreviouslyNonEmptyUnsupported() { 164 expectThrows(disjoint); 165 expectUnchanged(); 166 } 167 168 // retainAll(superset) 169 170 @CollectionFeature.Require(SUPPORTS_REMOVE) 171 public void testRetainAll_superset() { 172 expectReturnsFalse(superset); 173 expectUnchanged(); 174 } 175 176 @CollectionFeature.Require(absent = SUPPORTS_REMOVE) 177 public void testRetainAll_supersetUnsupported() { 178 expectReturnsFalseOrThrows(superset); 179 expectUnchanged(); 180 } 181 182 // retainAll(subset) 183 184 @CollectionFeature.Require(SUPPORTS_REMOVE) 185 @CollectionSize.Require(absent = {ZERO, ONE}) 186 public void testRetainAll_subset() { 187 expectReturnsTrue(nonEmptyProperSubset); 188 expectContents(nonEmptyProperSubset.toRetain); 189 } 190 191 @CollectionFeature.Require(absent = SUPPORTS_REMOVE) 192 @CollectionSize.Require(absent = {ZERO, ONE}) 193 public void testRetainAll_subsetUnsupported() { 194 expectThrows(nonEmptyProperSubset); 195 expectUnchanged(); 196 } 197 198 // retainAll(sameElements) 199 200 @CollectionFeature.Require(SUPPORTS_REMOVE) 201 public void testRetainAll_sameElements() { 202 expectReturnsFalse(sameElements); 203 expectUnchanged(); 204 } 205 206 @CollectionFeature.Require(absent = SUPPORTS_REMOVE) 207 public void testRetainAll_sameElementsUnsupported() { 208 expectReturnsFalseOrThrows(sameElements); 209 expectUnchanged(); 210 } 211 212 // retainAll(partialOverlap) 213 214 @CollectionFeature.Require(SUPPORTS_REMOVE) 215 @CollectionSize.Require(absent = {ZERO, ONE}) 216 public void testRetainAll_partialOverlap() { 217 expectReturnsTrue(partialOverlap); 218 expectContents(samples.e2); 219 } 220 221 @CollectionFeature.Require(absent = SUPPORTS_REMOVE) 222 @CollectionSize.Require(absent = {ZERO, ONE}) 223 public void testRetainAll_partialOverlapUnsupported() { 224 expectThrows(partialOverlap); 225 expectUnchanged(); 226 } 227 228 // retainAll(containsDuplicates) 229 230 @CollectionFeature.Require(SUPPORTS_REMOVE) 231 @CollectionSize.Require(ONE) 232 public void testRetainAll_containsDuplicatesSizeOne() { 233 expectReturnsFalse(containsDuplicates); 234 expectContents(samples.e0); 235 } 236 237 @CollectionFeature.Require(SUPPORTS_REMOVE) 238 @CollectionSize.Require(absent = {ZERO, ONE}) 239 public void testRetainAll_containsDuplicatesSizeSeveral() { 240 expectReturnsTrue(containsDuplicates); 241 expectContents(samples.e0); 242 } 243 244 // retainAll(nullSingleton) 245 246 @CollectionFeature.Require(SUPPORTS_REMOVE) 247 @CollectionSize.Require(ZERO) 248 public void testRetainAll_nullSingletonPreviouslyEmpty() { 249 expectReturnsFalse(nullSingleton); 250 expectUnchanged(); 251 } 252 253 @CollectionFeature.Require(SUPPORTS_REMOVE) 254 @CollectionSize.Require(absent = ZERO) 255 public void testRetainAll_nullSingletonPreviouslyNonEmpty() { 256 expectReturnsTrue(nullSingleton); 257 expectContents(); 258 } 259 260 @CollectionFeature.Require({SUPPORTS_REMOVE, ALLOWS_NULL_VALUES}) 261 @CollectionSize.Require(ONE) 262 public void testRetainAll_nullSingletonPreviouslySingletonWithNull() { 263 initCollectionWithNullElement(); 264 expectReturnsFalse(nullSingleton); 265 expectContents(createArrayWithNullElement()); 266 } 267 268 @CollectionFeature.Require({SUPPORTS_REMOVE, ALLOWS_NULL_VALUES}) 269 @CollectionSize.Require(absent = {ZERO, ONE}) 270 public void testRetainAll_nullSingletonPreviouslySeveralWithNull() { 271 initCollectionWithNullElement(); 272 expectReturnsTrue(nullSingleton); 273 expectContents(nullSingleton.toRetain); 274 } 275 276 // nullSingleton.retainAll() 277 278 @CollectionFeature.Require({SUPPORTS_REMOVE, ALLOWS_NULL_VALUES}) 279 @CollectionSize.Require(absent = ZERO) 280 public void testRetainAll_containsNonNullWithNull() { 281 initCollectionWithNullElement(); 282 expectReturnsTrue(disjoint); 283 expectContents(); 284 } 285 286 // retainAll(null) 287 288 /* 289 * AbstractCollection fails the retainAll(null) test when the subject 290 * collection is empty, but we'd still like to test retainAll(null) when we 291 * can. We split the test into empty and non-empty cases. This allows us to 292 * suppress only the former. 293 */ 294 295 @CollectionFeature.Require(SUPPORTS_REMOVE) 296 @CollectionSize.Require(ZERO) 297 public void testRetainAll_nullCollectionReferenceEmptySubject() { 298 try { 299 collection.retainAll(null); 300 // Returning successfully is not ideal, but tolerated. 301 } catch (NullPointerException expected) { 302 } 303 } 304 305 @CollectionFeature.Require(SUPPORTS_REMOVE) 306 @CollectionSize.Require(absent = ZERO) 307 public void testRetainAll_nullCollectionReferenceNonEmptySubject() { 308 try { 309 collection.retainAll(null); 310 fail("retainAll(null) should throw NullPointerException"); 311 } catch (NullPointerException expected) { 312 } 313 } 314 315 private void expectReturnsTrue(Target target) { 316 String message 317 = Platform.format("retainAll(%s) should return true", target); 318 assertTrue(message, collection.retainAll(target.toRetain)); 319 } 320 321 private void expectReturnsFalse(Target target) { 322 String message 323 = Platform.format("retainAll(%s) should return false", target); 324 assertFalse(message, collection.retainAll(target.toRetain)); 325 } 326 327 private void expectThrows(Target target) { 328 try { 329 collection.retainAll(target.toRetain); 330 String message = Platform.format("retainAll(%s) should throw", target); 331 fail(message); 332 } catch (UnsupportedOperationException expected) { 333 } 334 } 335 336 private void expectReturnsFalseOrThrows(Target target) { 337 String message 338 = Platform.format("retainAll(%s) should return false or throw", target); 339 try { 340 assertFalse(message, collection.retainAll(target.toRetain)); 341 } catch (UnsupportedOperationException tolerated) { 342 } 343 } 344} 345