001/*
002 * Licensed to the Apache Software Foundation (ASF) under one or more
003 * contributor license agreements.  See the NOTICE file distributed with
004 * this work for additional information regarding copyright ownership.
005 * The ASF licenses this file to You under the Apache License, Version 2.0
006 * (the "License"); you may not use this file except in compliance with
007 * the License.  You may obtain a copy of the License at
008 *
009 *     http://www.apache.org/licenses/LICENSE-2.0
010 *
011 * Unless required by applicable law or agreed to in writing, software
012 * distributed under the License is distributed on an "AS IS" BASIS,
013 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
014 * See the License for the specific language governing permissions and
015 * limitations under the License.
016 */
017package org.apache.commons.collections.primitives;
018
019import java.io.Serializable;
020import java.util.ArrayList;
021import java.util.ConcurrentModificationException;
022import java.util.List;
023
024import org.apache.commons.collections.primitives.adapters.BaseTestList;
025import org.apache.commons.collections.primitives.adapters.BooleanListList;
026import org.apache.commons.collections.primitives.adapters.ListBooleanList;
027
028/**
029 * @version $Revision: 480451 $ $Date: 2006-11-29 02:45:08 -0500 (Wed, 29 Nov 2006) $
030 * @author Rodney Waldhoff
031 */
032public abstract class TestBooleanList extends BaseTestList {
033
034    // conventional
035    // ------------------------------------------------------------------------
036
037    public TestBooleanList(String testName) {
038        super(testName);
039    }
040
041    // collections testing framework
042    // ------------------------------------------------------------------------
043
044    // collections testing framework: boolean list
045    // ------------------------------------------------------------------------
046
047    protected abstract BooleanList makeEmptyBooleanList();
048
049    protected BooleanList makeFullBooleanList() {
050        BooleanList list = makeEmptyBooleanList();
051        boolean[] values = getFullBooleans();
052        for(int i=0;i<values.length;i++) {
053            list.add(values[i]);
054        }
055        return list;
056    }
057
058    protected boolean[] getFullBooleans() {
059        boolean[] result = new boolean[19];
060        for(int i = 0; i < result.length; i++) {
061            result[i] = true;
062        }
063        return result;
064    }
065
066    protected boolean[] getOtherBooleans() {
067        boolean[] result = new boolean[19];
068        for(int i = 0; i < result.length; i++) {
069            result[i] = false;
070        }
071        return result;
072    }
073    
074    // collections testing framework: inherited
075    // ------------------------------------------------------------------------
076
077    public List makeEmptyList() {
078        return new BooleanListList(makeEmptyBooleanList());
079    }
080        
081    public Object[] getFullElements() {
082        return wrapArray(getFullBooleans());
083    }
084
085    public Object[] getOtherElements() {
086        return wrapArray(getOtherBooleans());
087    }
088
089    // private utils
090    // ------------------------------------------------------------------------
091
092    private Boolean[] wrapArray(boolean[] primitives) {
093        Boolean[] result = new Boolean[primitives.length];
094        for(int i=0;i<result.length;i++) {
095            result[i] = new Boolean(primitives[i]);            
096        }
097        return result;
098    }
099
100    // tests
101    // ------------------------------------------------------------------------
102
103    public void testExceptionOnConcurrentModification() {
104        BooleanList list = makeFullBooleanList();
105        BooleanIterator iter = list.iterator();
106        iter.next();
107        list.add(true);
108        try {
109            iter.next();
110            fail("Expected ConcurrentModificationException");
111        } catch(ConcurrentModificationException e) {
112            // expected
113        }
114    }
115    
116    public void testAddAllBooleanListAtIndex() {
117        BooleanList source = makeFullBooleanList();
118        BooleanList dest = makeFullBooleanList();
119        dest.addAll(1,source);
120        
121        BooleanIterator iter = dest.iterator();
122        assertTrue(iter.hasNext());
123        assertEquals(source.get(0),iter.next());
124        for(int i=0;i<source.size();i++) {
125            assertTrue(iter.hasNext());
126            assertEquals(source.get(i),iter.next());
127        }
128        for(int i=1;i<source.size();i++) {
129            assertTrue(iter.hasNext());
130            assertEquals(source.get(i),iter.next());
131        }
132        assertFalse(iter.hasNext());
133    }
134    
135    public void testToJustBigEnoughBooleanArray() {
136        BooleanList list = makeFullBooleanList();
137        boolean[] dest = new boolean[list.size()];
138        assertSame(dest,list.toArray(dest));
139        int i=0;
140        for(BooleanIterator iter = list.iterator(); iter.hasNext();i++) {
141            assertEquals(iter.next(),dest[i]);
142        }
143    }
144    
145    public void testToLargerThanNeededBooleanArray() {
146        BooleanList list = makeFullBooleanList();
147        boolean[] dest = new boolean[list.size()*2];
148        for(int i=0;i<dest.length;i++) {
149            dest[i] = true;
150        }       
151        assertSame(dest,list.toArray(dest));
152        int i=0;
153        for(BooleanIterator iter = list.iterator(); iter.hasNext();i++) {
154            assertEquals(iter.next(),dest[i]);
155        }
156        for(;i<dest.length;i++) {
157            assertEquals(true,dest[i]);
158        }
159    }
160    
161    public void testToSmallerThanNeededBooleanArray() {
162        BooleanList list = makeFullBooleanList();
163        boolean[] dest = new boolean[list.size()/2];
164        boolean[] dest2 = list.toArray(dest);
165        assertTrue(dest != dest2);
166        int i=0;
167        for(BooleanIterator iter = list.iterator(); iter.hasNext();i++) {
168            assertEquals(iter.next(),dest2[i]);
169        }
170    }
171
172    public void testHashCodeSpecification() {
173        BooleanList list = makeFullBooleanList();
174        int hash = 1;
175        for(BooleanIterator iter = list.iterator(); iter.hasNext(); ) {
176            hash = 31*hash + new Boolean(iter.next()).hashCode();
177        }
178        assertEquals(hash,list.hashCode());
179    }
180    
181    public void testEqualsWithTwoBooleanLists() {
182        BooleanList one = makeEmptyBooleanList();
183        assertEquals("Equals is reflexive on empty list",one,one);
184        BooleanList two = makeEmptyBooleanList();
185        assertEquals("Empty lists are equal",one,two);
186        assertEquals("Equals is symmetric on empty lists",two,one);
187        
188        one.add(true);
189        assertEquals("Equals is reflexive on non empty list",one,one);
190        assertTrue(!one.equals(two));
191        assertTrue(!two.equals(one));
192
193        two.add(true);
194        assertEquals("Non empty lists are equal",one,two);
195        assertEquals("Equals is symmetric on non empty list",one,two);
196        
197        one.add(true); one.add(false);
198        one.add(true); one.add(false);
199        one.add(true); one.add(false);
200        assertEquals("Equals is reflexive on larger non empty list",one,one);
201        assertTrue(!one.equals(two));
202        assertTrue(!two.equals(one));
203        
204        two.add(true); two.add(false);
205        two.add(true); two.add(false);
206        two.add(true); two.add(false);
207        assertEquals("Larger non empty lists are equal",one,two);
208        assertEquals("Equals is symmetric on larger non empty list",two,one);
209
210        one.add(true);
211        two.add(false);
212        assertTrue(!one.equals(two));
213        assertTrue(!two.equals(one));
214
215    }
216
217    public void testBooleanSubListEquals() {
218        BooleanList one = makeEmptyBooleanList();
219        assertEquals(one,one.subList(0,0));
220        assertEquals(one.subList(0,0),one);
221        
222        one.add(true);
223        assertEquals(one,one.subList(0,1));
224        assertEquals(one.subList(0,1),one);
225
226        one.add(true); one.add(false); one.add(true); one.add(true); one.add(false); one.add(false);
227        assertEquals(one.subList(0,4),one.subList(0,4));
228        assertEquals(one.subList(3,5),one.subList(3,5));
229    }
230    
231    public void testEqualsWithBooleanListAndList() {
232        BooleanList ilist = makeEmptyBooleanList();
233        List list = new ArrayList();
234        
235        assertTrue("Unwrapped, empty List should not be equal to empty BooleanList.",!ilist.equals(list));
236        assertTrue("Unwrapped, empty BooleanList should not be equal to empty List.",!list.equals(ilist));
237        
238        assertEquals(new ListBooleanList(list),ilist);
239        assertEquals(ilist,new ListBooleanList(list));
240        assertEquals(new BooleanListList(ilist),list);
241        assertEquals(list,new BooleanListList(ilist));
242        
243        ilist.add(true);
244        list.add(new Boolean(true));
245
246        assertTrue("Unwrapped, non-empty List is not equal to non-empty BooleanList.",!ilist.equals(list));
247        assertTrue("Unwrapped, non-empty BooleanList is not equal to non-empty List.",!list.equals(ilist));
248        
249        assertEquals(new ListBooleanList(list),ilist);
250        assertEquals(ilist,new ListBooleanList(list));
251        assertEquals(new BooleanListList(ilist),list);
252        assertEquals(list,new BooleanListList(ilist));
253                
254        ilist.add(true); ilist.add(false); ilist.add(true); ilist.add(true); ilist.add(false);
255        list.add(new Boolean(true)); list.add(Boolean.FALSE); list.add(Boolean.TRUE); list.add(Boolean.TRUE); list.add(new Boolean(false));
256
257        assertTrue("Unwrapped, non-empty List is not equal to non-empty BooleanList.",!ilist.equals(list));
258        assertTrue("Unwrapped, non-empty BooleanList is not equal to non-empty List.",!list.equals(ilist));
259        
260        assertEquals(new ListBooleanList(list),ilist);
261        assertEquals(ilist,new ListBooleanList(list));
262        assertEquals(new BooleanListList(ilist),list);
263        assertEquals(list,new BooleanListList(ilist));
264        
265    }
266
267    public void testClearAndSize() {
268        BooleanList list = makeEmptyBooleanList();
269        assertEquals(0, list.size());
270        for(int i = 0; i < 100; i++) {
271            list.add(i%2==0);
272        }
273        assertEquals(100, list.size());
274        list.clear();
275        assertEquals(0, list.size());
276    }
277
278    public void testRemoveViaSubList() {
279        BooleanList list = makeEmptyBooleanList();
280        for(int i = 0; i < 100; i++) {
281            list.add(i%2==0);
282        }
283        BooleanList sub = list.subList(25,75);
284        assertEquals(50,sub.size());
285        for(int i = 0; i < 50; i++) {
286            assertEquals(100-i,list.size());
287            assertEquals(50-i,sub.size());
288            assertEquals((25+i)%2==0,sub.removeElementAt(0));
289            assertEquals(50-i-1,sub.size());
290            assertEquals(100-i-1,list.size());
291        }
292        assertEquals(0,sub.size());
293        assertEquals(50,list.size());        
294    }
295    
296    public void testAddGet() {
297        BooleanList list = makeEmptyBooleanList();
298        for (int i = 0; i < 255; i++) {
299            list.add(i%2==0);
300        }
301        for (int i = 0; i < 255; i++) {
302            assertEquals(i%2==0, list.get(i));
303        }
304    }
305
306    public void testAddAndShift() {
307        BooleanList list = makeEmptyBooleanList();
308        list.add(0, true);
309        assertEquals("Should have one entry", 1, list.size());
310        list.add(true);
311        list.add(false);
312        list.add(1, false);
313        for(int i = 0; i < 4; i++) {
314            assertEquals("Should get entry back", (i%2==0), list.get(i));
315        }
316    }
317
318    public void testIsSerializable() throws Exception {
319        BooleanList list = makeFullBooleanList();
320        assertTrue(list instanceof Serializable);
321        byte[] ser = writeExternalFormToBytes((Serializable)list);
322        BooleanList deser = (BooleanList)(readExternalFormFromBytes(ser));
323        assertEquals(list,deser);
324        assertEquals(deser,list);
325    }
326
327    public void testBooleanListSerializeDeserializeThenCompare() throws Exception {
328        BooleanList list = makeFullBooleanList();
329        if(list instanceof Serializable) {
330            byte[] ser = writeExternalFormToBytes((Serializable)list);
331            BooleanList deser = (BooleanList)(readExternalFormFromBytes(ser));
332            assertEquals("obj != deserialize(serialize(obj))",list,deser);
333        }
334    }
335
336    public void testSubListsAreNotSerializable() throws Exception {
337        BooleanList list = makeFullBooleanList().subList(2,3);
338        assertTrue( ! (list instanceof Serializable) );
339    }
340
341    public void testSubListOutOfBounds() throws Exception {
342        try {
343            makeEmptyBooleanList().subList(2,3);
344            fail("Expected IndexOutOfBoundsException");
345        } catch(IndexOutOfBoundsException e) {
346            // expected
347        }
348
349        try {
350            makeFullBooleanList().subList(-1,3);
351            fail("Expected IndexOutOfBoundsException");
352        } catch(IndexOutOfBoundsException e) {
353            // expected
354        }
355
356
357        try {
358            makeFullBooleanList().subList(5,2);
359            fail("Expected IllegalArgumentException");
360        } catch(IllegalArgumentException e) {
361            // expected
362        }
363
364        try {
365            makeFullBooleanList().subList(2,makeFullBooleanList().size()+2);
366            fail("Expected IndexOutOfBoundsException");
367        } catch(IndexOutOfBoundsException e) {
368            // expected
369        }
370    }
371
372    public void testListIteratorOutOfBounds() throws Exception {
373        try {
374            makeEmptyBooleanList().listIterator(2);
375            fail("Expected IndexOutOfBoundsException");
376        } catch(IndexOutOfBoundsException e) {
377            // expected
378        }
379
380        try {
381            makeFullBooleanList().listIterator(-1);
382            fail("Expected IndexOutOfBoundsException");
383        } catch(IndexOutOfBoundsException e) {
384            // expected
385        }
386
387        try {
388            makeFullBooleanList().listIterator(makeFullBooleanList().size()+2);
389            fail("Expected IndexOutOfBoundsException");
390        } catch(IndexOutOfBoundsException e) {
391            // expected
392        }
393    }
394
395    public void testListIteratorSetWithoutNext() throws Exception {
396        BooleanListIterator iter = makeFullBooleanList().listIterator();
397        try {
398            iter.set(true);
399            fail("Expected IllegalStateException");
400        } catch(IllegalStateException e) {
401            // expected
402        }
403    }
404
405    public void testListIteratorSetAfterRemove() throws Exception {
406        BooleanListIterator iter = makeFullBooleanList().listIterator();
407        iter.next();
408        iter.remove();
409        try {            
410            iter.set(true);
411            fail("Expected IllegalStateException");
412        } catch(IllegalStateException e) {
413            // expected
414        }
415    }
416
417    public void testCollectionRemoveAll() {
418        // Super's impl doesn't work because there are only two unique values in my list.
419        BooleanList trueList = new ArrayBooleanList();
420        trueList.add(true);
421        trueList.add(true);
422        trueList.add(true);
423        trueList.add(true);
424        trueList.add(true);
425        BooleanList falseList = new ArrayBooleanList();
426        falseList.add(false);
427        falseList.add(false);
428        falseList.add(false);
429        falseList.add(false);
430        falseList.add(false);
431
432        BooleanList list = new ArrayBooleanList();
433        assertTrue(list.isEmpty());
434        assertFalse(list.removeAll(trueList));        
435        assertTrue(list.isEmpty());
436        
437        list.add(false);
438        list.add(false);
439        assertEquals(2,list.size());
440        assertFalse(list.removeAll(trueList));        
441        assertEquals(2,list.size());
442        
443        list.add(true);
444        list.add(false);
445        list.add(true);
446        assertEquals(5,list.size());
447        assertTrue(list.removeAll(trueList));        
448        assertEquals(3,list.size());
449        
450        for(BooleanIterator iter = list.iterator(); iter.hasNext();) {
451            assertEquals(false,iter.next());
452        }
453
454        assertFalse(list.removeAll(trueList));        
455        assertEquals(3,list.size());
456        
457        for(BooleanIterator iter = list.iterator(); iter.hasNext();) {
458            assertEquals(false,iter.next());
459        }
460
461        assertTrue(list.removeAll(falseList));        
462        assertTrue(list.isEmpty());
463    }
464
465    public void testCollectionRetainAll() {
466        // Super's impl doesn't work because there are only two unique values in my list.
467        BooleanList trueList = new ArrayBooleanList();
468        trueList.add(true);
469        BooleanList falseList = new ArrayBooleanList();
470        falseList.add(false);
471
472        BooleanList list = new ArrayBooleanList();
473        assertTrue(list.isEmpty());
474        assertFalse(list.retainAll(falseList));        
475        assertTrue(list.isEmpty());
476        
477        list.add(false);
478        list.add(false);
479        assertEquals(2,list.size());
480        assertFalse(list.retainAll(falseList));        
481        assertEquals(2,list.size());
482        
483        list.add(true);
484        list.add(false);
485        list.add(true);
486        assertEquals(5,list.size());
487        assertTrue(list.retainAll(falseList));        
488        assertEquals(3,list.size());
489        
490        for(BooleanIterator iter = list.iterator(); iter.hasNext();) {
491            assertEquals(false,iter.next());
492        }
493
494        assertFalse(list.retainAll(falseList));        
495        assertEquals(3,list.size());
496        
497        for(BooleanIterator iter = list.iterator(); iter.hasNext();) {
498            assertEquals(false,iter.next());
499        }
500
501        assertTrue(list.retainAll(trueList));        
502        assertTrue(list.isEmpty());
503    }
504
505    public void testListEquals() {
506        // Super type doesn't work because there are only two unique values in my list.
507    }
508}