KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > org > ozoneDB > collections > AbstractOzoneCollection


1 /*
2  * $Id: AbstractOzoneCollection.java,v 1.5 2003/11/05 11:50:06 leomekenkamp Exp $
3  * This file is based on AbstractCollection.java from GNU Classpath. Quote:
4  
5 AbstractCollection.java -- Abstract implementation of most of Collection
6 Copyright (C) 1998, 2000, 2001 Free Software Foundation, Inc.
7  
8 This file is part of GNU Classpath.
9  
10 GNU Classpath is free software; you can redistribute it and/or modify
11 it under the terms of the GNU General Public License as published by
12 the Free Software Foundation; either version 2, or (at your option)
13 any later version.
14  
15 GNU Classpath is distributed in the hope that it will be useful, but
16 WITHOUT ANY WARRANTY; without even the implied warranty of
17 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
18 General Public License for more details.
19  
20 You should have received a copy of the GNU General Public License
21 along with GNU Classpath; see the file COPYING. If not, write to the
22 Free Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
23 02111-1307 USA.
24  
25 Linking this library statically or dynamically with other modules is
26 making a combined work based on this library. Thus, the terms and
27 conditions of the GNU General Public License cover the whole
28 combination.
29  
30 As a special exception, the copyright holders of this library give you
31 permission to link this library with independent modules to produce an
32 executable, regardless of the license terms of these independent
33 modules, and to copy and distribute the resulting executable under
34 terms of your choice, provided that you also meet, for each linked
35 independent module, the terms and conditions of the license of that
36 module. An independent module is a module which is not derived from
37 or based on this library. If you modify this library, you may extend
38 this exception to your version of the library, but you are not
39 obligated to do so. If you do not wish to do so, delete this
40 exception statement from your version.
41  
42  * end quote.
43  *
44  * This file is licenced under the same conditions as its original (GPL +
45  * "special exception").
46  */

47
48 package org.ozoneDB.collections;
49
50 import java.lang.reflect.Array JavaDoc;
51 import java.util.Collection JavaDoc;
52 import java.util.Iterator JavaDoc;
53 import org.ozoneDB.OzoneObject;
54
55 /**
56  * <p>
57  * A basic implementation of most of the methods in the Collection interface to
58  * make it easier to create a collection. To create an unmodifiable Collection,
59  * just subclass AbstractOzoneCollection and provide implementations of the
60  * iterator() and size() methods. The Iterator returned by iterator() need only
61  * provide implementations of hasNext() and next() (that is, it may throw an
62  * UnsupportedOperationException if remove() is called). To create a modifiable
63  * Collection, you must in addition provide an implementation of the
64  * add(Object) method and the Iterator returned by iterator() must provide an
65  * implementation of remove(). Other methods should be overridden if the
66  * backing data structure allows for a more efficient implementation. The
67  * precise implementation used by AbstractOzoneCollection is documented, so that
68  * subclasses can tell which methods could be implemented more efficiently.
69  * </p><p>
70  * The programmer should provide a no-argument constructor, and one that
71  * accepts another Collection, as recommended by the Collection interface.
72  * Unfortunately, there is no way to enforce this in Java.
73  * </p>
74  *
75  * @author Original author unknown
76  * @author Bryce McKinlay
77  * @author Eric Blake <ebb9@email.byu.edu>
78  * @author <a HREF="mailto:ozoneATmekenkampD0Tcom">Leo Mekenkamp (mind the anti-sp@m)</a> (adaptation for ozone)
79  * @see java.util.AbstractCollection
80  */

81 public abstract class AbstractOzoneCollection extends OzoneObject implements OzoneCollection {
82     
83     private static final long serialVersionUID = 1L;
84     
85     protected AbstractOzoneCollection() {
86     }
87     
88     /**
89      * Return an Iterator over this collection. The iterator must provide the
90      * hasNext and next methods and should in addition provide remove if the
91      * collection is modifiable.
92      *
93      * @return an iterator
94      */

95     public abstract Iterator JavaDoc iterator();
96     
97     /**
98      * Return the number of elements in this collection. If there are more than
99      * Integer.MAX_VALUE elements, return Integer.MAX_VALUE.
100      *
101      * @return the size
102      */

103     public abstract int size();
104     
105     /**
106      * Add an object to the collection (optional operation). This implementation
107      * always throws an UnsupportedOperationException - it should be
108      * overridden if the collection is to be modifiable. If the collection
109      * does not accept duplicates, simply return false. Collections may specify
110      * limitations on what may be added.
111      *
112      * @param o the object to add
113      * @return true if the add operation caused the Collection to change
114      * @throws UnsupportedOperationException if the add operation is not
115      * supported on this collection
116      * @throws NullPointerException if the collection does not support null
117      * @throws ClassCastException if the object is of the wrong type
118      * @throws IllegalArgumentException if some aspect of the object prevents
119      * it from being added
120      */

121     public boolean add(Object JavaDoc o) {
122         throw new UnsupportedOperationException JavaDoc();
123     }
124     
125     /**
126      * Add all the elements of a given collection to this collection (optional
127      * operation). This implementation obtains an Iterator over the given
128      * collection and iterates over it, adding each element with the
129      * add(Object) method (thus this method will fail with an
130      * UnsupportedOperationException if the add method does). The behavior is
131      * unspecified if the specified collection is modified during the iteration,
132      * including the special case of trying addAll(this) on a non-empty
133      * collection.
134      *
135      * @param c the collection to add the elements of to this collection
136      * @return true if the add operation caused the Collection to change
137      * @throws UnsupportedOperationException if the add operation is not
138      * supported on this collection
139      * @throws NullPointerException if this collection does not support null,
140      * or if the specified collection is null
141      * @throws ClassCastException if an object in c is of the wrong type
142      * @throws IllegalArgumentException if some aspect of an object in c prevents
143      * it from being added
144      * @see #add(Object)
145      */

146     public boolean addAll(Collection JavaDoc c) {
147         Iterator JavaDoc itr;
148         if (c instanceof OzoneCollection) {
149             itr = ((OzoneCollection) c)._org_ozoneDB_internalIterator();
150         } else {
151             itr = c.iterator();
152         }
153         boolean modified = false;
154         int pos = c.size();
155         while (--pos >= 0)
156             modified |= add(itr.next());
157         return modified;
158     }
159     
160     /**
161      * Remove all elements from the collection (optional operation). This
162      * implementation obtains an iterator over the collection and calls next
163      * and remove on it repeatedly (thus this method will fail with an
164      * UnsupportedOperationException if the Iterator's remove method does)
165      * until there are no more elements to remove.
166      * Many implementations will have a faster way of doing this.
167      *
168      * @throws UnsupportedOperationException if the Iterator returned by
169      * iterator does not provide an implementation of remove
170      * @see Iterator#remove()
171      */

172     public void clear() {
173         Iterator JavaDoc itr = _org_ozoneDB_internalIterator();
174         int pos = size();
175         while (--pos >= 0) {
176             itr.next();
177             itr.remove();
178         }
179     }
180     
181     /**
182      * Test whether this collection contains a given object. That is, if the
183      * collection has an element e such that (o == null ? e == null :
184      * o.equals(e)). This implementation obtains an iterator over the collection
185      * and iterates over it, testing each element for equality with the given
186      * object. If it is equal, true is returned. Otherwise false is returned when
187      * the end of the collection is reached.
188      *
189      * @param o the object to remove from this collection
190      * @return true if this collection contains an object equal to o
191      */

192     public boolean contains(Object JavaDoc o) {
193         Iterator JavaDoc itr = _org_ozoneDB_internalIterator();
194         int pos = size();
195         while (--pos >= 0)
196             if (equals(o, itr.next()))
197                 return true;
198         return false;
199     }
200     
201     /**
202      * Tests whether this collection contains all the elements in a given
203      * collection. This implementation iterates over the given collection,
204      * testing whether each element is contained in this collection. If any one
205      * is not, false is returned. Otherwise true is returned.
206      *
207      * @param c the collection to test against
208      * @return true if this collection contains all the elements in the given
209      * collection
210      * @throws NullPointerException if the given collection is null
211      * @see #contains(Object)
212      */

213     public boolean containsAll(Collection JavaDoc c) {
214         Iterator JavaDoc itr;
215         if (c instanceof OzoneCollection) {
216             itr = ((OzoneCollection) c)._org_ozoneDB_internalIterator();
217         } else {
218             itr = c.iterator();
219         }
220         int pos = c.size();
221         while (--pos >= 0)
222             if (!contains(itr.next()))
223                 return false;
224         return true;
225     }
226     
227     /**
228      * Test whether this collection is empty. This implementation returns
229      * size() == 0.
230      *
231      * @return true if this collection is empty.
232      * @see #size()
233      */

234     public boolean isEmpty() {
235         return size() == 0;
236     }
237     
238     /**
239      * Remove a single instance of an object from this collection (optional
240      * operation). That is, remove one element e such that
241      * <code>(o == null ? e == null : o.equals(e))</code>, if such an element
242      * exists. This implementation obtains an iterator over the collection
243      * and iterates over it, testing each element for equality with the given
244      * object. If it is equal, it is removed by the iterator's remove method
245      * (thus this method will fail with an UnsupportedOperationException if
246      * the Iterator's remove method does). After the first element has been
247      * removed, true is returned; if the end of the collection is reached, false
248      * is returned.
249      *
250      * @param o the object to remove from this collection
251      * @return true if the remove operation caused the Collection to change, or
252      * equivalently if the collection did contain o.
253      * @throws UnsupportedOperationException if this collection's Iterator
254      * does not support the remove method
255      * @see Iterator#remove()
256      */

257     public boolean remove(Object JavaDoc o) {
258         Iterator JavaDoc itr = _org_ozoneDB_internalIterator();
259         int pos = size();
260         while (--pos >= 0)
261             if (equals(o, itr.next())) {
262                 itr.remove();
263                 return true;
264             }
265         return false;
266     }
267     
268     /**
269      * Remove from this collection all its elements that are contained in a given
270      * collection (optional operation). This implementation iterates over this
271      * collection, and for each element tests if it is contained in the given
272      * collection. If so, it is removed by the Iterator's remove method (thus
273      * this method will fail with an UnsupportedOperationException if the
274      * Iterator's remove method does).
275      *
276      * @param c the collection to remove the elements of
277      * @return true if the remove operation caused the Collection to change
278      * @throws UnsupportedOperationException if this collection's Iterator
279      * does not support the remove method
280      * @see Iterator#remove()
281      */

282     public boolean removeAll(Collection JavaDoc c) {
283         return removeAllInternal(c);
284     }
285     
286     /**
287      * Remove from this collection all its elements that are contained in a given
288      * collection (optional operation). This implementation iterates over this
289      * collection, and for each element tests if it is contained in the given
290      * collection. If so, it is removed by the Iterator's remove method (thus
291      * this method will fail with an UnsupportedOperationException if the
292      * Iterator's remove method does). This method is necessary for ArrayList,
293      * which cannot publicly override removeAll but can optimize this call.
294      *
295      * @param c the collection to remove the elements of
296      * @return true if the remove operation caused the Collection to change
297      * @throws UnsupportedOperationException if this collection's Iterator
298      * does not support the remove method
299      * @see Iterator#remove()
300      */

301     boolean removeAllInternal(Collection JavaDoc c) {
302         Iterator JavaDoc itr;
303         if (c instanceof OzoneCollection) {
304             itr = ((OzoneCollection) c)._org_ozoneDB_internalIterator();
305         } else {
306             itr = c.iterator();
307         }
308         boolean modified = false;
309         int pos = size();
310         while (--pos >= 0)
311             if (c.contains(itr.next())) {
312                 itr.remove();
313                 modified = true;
314             }
315         return modified;
316     }
317     
318     /**
319      * Remove from this collection all its elements that are not contained in a
320      * given collection (optional operation). This implementation iterates over
321      * this collection, and for each element tests if it is contained in the
322      * given collection. If not, it is removed by the Iterator's remove method
323      * (thus this method will fail with an UnsupportedOperationException if
324      * the Iterator's remove method does).
325      *
326      * @param c the collection to retain the elements of
327      * @return true if the remove operation caused the Collection to change
328      * @throws UnsupportedOperationException if this collection's Iterator
329      * does not support the remove method
330      * @see Iterator#remove()
331      */

332     public boolean retainAll(Collection JavaDoc c) {
333         return retainAllInternal(c);
334     }
335     
336     /**
337      * Remove from this collection all its elements that are not contained in a
338      * given collection (optional operation). This implementation iterates over
339      * this collection, and for each element tests if it is contained in the
340      * given collection. If not, it is removed by the Iterator's remove method
341      * (thus this method will fail with an UnsupportedOperationException if
342      * the Iterator's remove method does). This method is necessary for
343      * ArrayList, which cannot publicly override retainAll but can optimize
344      * this call.
345      *
346      * @param c the collection to retain the elements of
347      * @return true if the remove operation caused the Collection to change
348      * @throws UnsupportedOperationException if this collection's Iterator
349      * does not support the remove method
350      * @see Iterator#remove()
351      */

352     boolean retainAllInternal(Collection JavaDoc c) {
353         Iterator JavaDoc itr;
354         if (c instanceof OzoneCollection) {
355             itr = ((OzoneCollection) c)._org_ozoneDB_internalIterator();
356         } else {
357             itr = c.iterator();
358         }
359         boolean modified = false;
360         int pos = size();
361         while (--pos >= 0)
362             if (!c.contains(itr.next())) {
363                 itr.remove();
364                 modified = true;
365             }
366         return modified;
367     }
368     
369     /**
370      * Return an array containing the elements of this collection. This
371      * implementation creates an Object array of size size() and then iterates
372      * over the collection, setting each element of the array from the value
373      * returned by the iterator. The returned array is safe, and is not backed
374      * by the collection.
375      *
376      * @return an array containing the elements of this collection
377      */

378     public Object JavaDoc[] toArray() {
379         Iterator JavaDoc itr = _org_ozoneDB_internalIterator();
380         int size = size();
381         Object JavaDoc[] a = new Object JavaDoc[size];
382         for (int pos = 0; pos < size; pos++)
383             a[pos] = itr.next();
384         return a;
385     }
386     
387     /**
388      * Copy the collection into a given array if it will fit, or into a
389      * dynamically created array of the same run-time type as the given array if
390      * not. If there is space remaining in the array, the first element after the
391      * end of the collection is set to null (this is only useful if the
392      * collection is known to contain no null elements, however). This
393      * implementation first tests whether the given array is large enough to hold
394      * all the elements of the collection. If not, the reflection API is used to
395      * allocate a new array of the same run-time type. Next an iterator is
396      * obtained over the collection and the elements are placed in the array as
397      * they are returned by the iterator. Finally the first spare element, if
398      * any, of the array is set to null, and the created array is returned.
399      * The returned array is safe; it is not backed by the collection. Note that
400      * null may not mark the last element, if the collection allows null
401      * elements.
402      *
403      * @param a the array to copy into, or of the correct run-time type
404      * @return the array that was produced
405      * @throws NullPointerException if the given array is null
406      * @throws ArrayStoreException if the type of the array precludes holding
407      * one of the elements of the Collection
408      */

409     public Object JavaDoc[] toArray(Object JavaDoc[] a) {
410         int size = size();
411         if (a.length < size)
412             a = (Object JavaDoc[]) Array.newInstance(a.getClass().getComponentType(),
413             size);
414         else if (a.length > size)
415             a[size] = null;
416         
417         Iterator JavaDoc itr = _org_ozoneDB_internalIterator();
418         for (int pos = 0; pos < size; pos++)
419             a[pos] = itr.next();
420         
421         return a;
422     }
423     
424     /**
425      * Creates a String representation of the Collection. The string returned is
426      * of the form "[a, b, ...]" where a and b etc are the results of calling
427      * toString on the elements of the collection. This implementation obtains an
428      * Iterator over the Collection and adds each element to a StringBuffer as it
429      * is returned by the iterator.
430      *
431      * @return a String representation of the Collection
432      */

433     public String JavaDoc toString() {
434         Iterator JavaDoc itr = _org_ozoneDB_internalIterator();
435         StringBuffer JavaDoc r = new StringBuffer JavaDoc("[");
436         for (int pos = size(); pos > 0; pos--) {
437             r.append(itr.next());
438             if (pos > 1)
439                 r.append(", ");
440         }
441         r.append("]");
442         return r.toString();
443     }
444     
445     /**
446      * Compare two objects according to Collection semantics.
447      *
448      * @param o1 the first object
449      * @param o2 the second object
450      * @return o1 == null ? o2 == null : o1.equals(o2)
451      */

452     // Package visible for use throughout java.util.
453
// It may be inlined since it is final.
454
static final boolean equals(Object JavaDoc o1, Object JavaDoc o2) {
455         return o1 == null ? o2 == null : o1.equals(o2);
456     }
457     
458     /**
459      * Hash an object according to Collection semantics.
460      *
461      * @param o the object to hash
462      * @return o1 == null ? 0 : o1.hashCode()
463      */

464     // Package visible for use throughout java.util.
465
// It may be inlined since it is final.
466
static final int hashCode(Object JavaDoc o) {
467         return o == null ? 0 : o.hashCode();
468     }
469
470     /** <p>Returns a non-ozone <code>Collection</code> that contains the same
471      * entries as this persistent one; it is (by nature of the client-server
472      * enviromnent) always a 'deep' copy of this <code>OzoneCollection</code>.
473      * I.e. the contents of this <code>OzoneCollection</code> instance are
474      * always copied to the client by use of serialization.</p>
475      * <p>This means that if this instance holds non-ozone objects, these
476      * objects are send to the calling client by means of serialization. If
477      * this instance holds ozone objects, it actually holds proxies to these
478      * objects. These proxies are copied and send to the client, resulting in
479      * different proxies to the same ozone objects.</p>
480      * <p>Note that all subclasses of <code>OzoneCollection</code> (or
481      * <code>OzoneMap</code>) have <code>getClientXxx()</code> member functions
482      * that returns a collection of type <code>Xxx</code>; these simply return
483      * a the same result value as <code>getClientCollection()</code>, without
484      * the need for a typecast.</p>
485      */

486     public Collection JavaDoc getClientCollection() {
487         throw new UnsupportedOperationException JavaDoc();
488     }
489     
490 }
Popular Tags