1 package org.djutils.immutablecollections; 2 3 import java.io.Serializable; 4 import java.util.Collection; 5 import java.util.Spliterator; 6 import java.util.Spliterators; 7 import java.util.stream.Stream; 8 import java.util.stream.StreamSupport; 9 10 /** 11 * A Collection interface without the methods that can change it. 12 * <p> 13 * Copyright (c) 2016-2024 Delft University of Technology, Jaffalaan 5, 2628 BX Delft, the Netherlands. All rights reserved. See 14 * for project information <a href="https://djutils.org" target="_blank"> https://djutils.org</a>. The DJUTILS project is 15 * distributed under a three-clause BSD-style license, which can be found at 16 * <a href="https://djutils.org/docs/license.html" target="_blank"> https://djutils.org/docs/license.html</a>. 17 * </p> 18 * @author <a href="https://www.tudelft.nl/averbraeck">Alexander Verbraeck</a> 19 * @author <a href="https://www.tudelft.nl/staff/p.knoppers/">Peter Knoppers</a> 20 * @param <E> the type of content of this Collection 21 */ 22 public interface ImmutableCollection<E> extends Iterable<E>, Serializable 23 { 24 /** 25 * Returns the number of elements in this immutable collection. If this immutable collection contains more than 26 * <code>Integer.MAX_VALUE</code> elements, returns <code>Integer.MAX_VALUE</code>. 27 * @return the number of elements in this immutable collection 28 */ 29 int size(); 30 31 /** 32 * Returns <code>true</code> if this immutable collection contains no elements. 33 * @return <code>true</code> if this immutable collection contains no elements 34 */ 35 boolean isEmpty(); 36 37 /** 38 * Returns <code>true</code> if this immutable collection contains the specified element. More formally, returns 39 * <code>true</code> if and only if this immutable collection contains at least one element <code>e</code> such that 40 * <code>(o==null ? e==null : o.equals(e))</code>. 41 * @param o Object; element whose presence in this immutable collection is to be tested 42 * @return <code>true</code> if this immutable collection contains the specified element 43 * @throws ClassCastException if the type of the specified element is incompatible with this immutable collection 44 * @throws NullPointerException if the specified element is null and this immutable collection does not permit null elements 45 */ 46 boolean contains(Object o); 47 48 /** 49 * Returns an immutable iterator over the elements in this immutable collection. There are no guarantees concerning the 50 * order in which the elements are returned (unless this immutable collection is an instance of some class that provides a 51 * guarantee). The ImmutableIterator is an Iterator where the remove() operation will throw an exception. 52 * @return an <code>ImmutableIterator</code> over the elements in this immutable collection 53 */ 54 @Override 55 ImmutableIterator<E> iterator(); 56 57 /** 58 * Returns an array containing all of the elements in this immutable collection. If this immutable collection makes any 59 * guarantees as to what order its elements are returned by its iterator, this method must return the elements in the same 60 * order. 61 * <p> 62 * See java.util.Collection.toArray() for more details. 63 * @return an array containing all of the elements in this immutable collection 64 */ 65 Object[] toArray(); 66 67 /** 68 * Returns an array containing all of the elements in this immutable collection; the runtime type of the returned array is 69 * that of the specified array. If the immutable collection fits in the specified array, it is returned therein. Otherwise, 70 * a new array is allocated with the runtime type of the specified array and the size of this immutable collection. 71 * <p> 72 * See java.util.Collection.toArray(T[]) for more details. 73 * @param <T> the runtime type of the array to contain the immutable collection 74 * @param a the array into which the elements of this immutable collection are to be stored, if it is big enough; otherwise, 75 * a new array of the same runtime type is allocated for this purpose. 76 * @return an array containing all of the elements in this immutable collection 77 * @throws ArrayStoreException if the runtime type of the specified array is not a supertype of the runtime type of every 78 * element in this immutable collection 79 * @throws NullPointerException if the specified array is null 80 */ 81 <T> T[] toArray(T[] a); 82 83 /** 84 * Returns <code>true</code> if this immutable collection contains all of the elements in the specified collection. 85 * @param c Collection<?>; collection to be checked for containment in this immutable collection 86 * @return <code>true</code> if this immutable collection contains all of the elements in the specified collection 87 * @throws ClassCastException if the types of one or more elements in the specified collection are incompatible with this 88 * immutable collection 89 * @throws NullPointerException if the specified collection contains one or more null elements and this immutable collection 90 * does not permit null elements, or if the specified collection is null. 91 * @see #contains(Object) 92 */ 93 boolean containsAll(Collection<?> c); 94 95 /** 96 * Returns <code>true</code> if this immutable collection contains all of the elements in the specified immutable 97 * collection. 98 * @param c ImmutableCollection<?>; immutable collection to be checked for containment in this immutable collection 99 * @return <code>true</code> if this immutable collection contains all of the elements in the specified immutable collection 100 * @throws ClassCastException if the types of one or more elements in the specified immutable collection are incompatible 101 * with this immutable collection 102 * @throws NullPointerException if the specified immutable collection contains one or more null elements and this immutable 103 * collection does not permit null elements, or if the specified immutable collection is null. 104 * @see #contains(Object) 105 */ 106 boolean containsAll(ImmutableCollection<?> c); 107 108 /** 109 * Creates a Spliterator over the elements in this collection. Implementations should document characteristic values 110 * reported by the spliterator. See java.util.Collection for more information. 111 * @return a {@code Spliterator} over the elements in this collection 112 */ 113 @Override 114 default Spliterator<E> spliterator() 115 { 116 return Spliterators.spliterator(toCollection(), 0); 117 } 118 119 /** 120 * Returns a sequential {@code Stream} with this collection as its source. 121 * <p> 122 * This method should be overridden when the {@link #spliterator()} method cannot return a spliterator that is 123 * {@code IMMUTABLE}, {@code CONCURRENT}, or <em>late-binding</em>. (See {@link #spliterator()} for details.) 124 * @return a sequential {@code Stream} over the elements in this collection 125 */ 126 default Stream<E> stream() 127 { 128 return StreamSupport.stream(spliterator(), false); 129 } 130 131 /** 132 * Returns a possibly parallel {@code Stream} with this collection as its source. It is allowable for this method to return 133 * a sequential stream. 134 * <p> 135 * This method should be overridden when the {@link #spliterator()} method cannot return a spliterator that is 136 * {@code IMMUTABLE}, {@code CONCURRENT}, or <em>late-binding</em>. (See {@link #spliterator()} for details.) 137 * @return a possibly parallel {@code Stream} over the elements in this collection 138 */ 139 default Stream<E> parallelStream() 140 { 141 return StreamSupport.stream(spliterator(), true); 142 } 143 144 /** 145 * Returns a modifiable copy of this immutable collection. 146 * @return a modifiable copy of this immutable collection. 147 */ 148 Collection<E> toCollection(); 149 150 /** 151 * Force to redefine equals for the implementations of immutable collection classes. 152 * @param obj Object; the object to compare this collection with 153 * @return whether the objects are equal 154 */ 155 @Override 156 boolean equals(Object obj); 157 158 /** 159 * Force to redefine hashCode for the implementations of immutable collection classes. 160 * @return the calculated hashCode 161 */ 162 @Override 163 int hashCode(); 164 165 /** 166 * Return whether the internal storage is a wrapped pointer to the original collection. If true, this means that anyone 167 * holding a pointer to this data structure can still change it. The users of the ImmutableCollection itself can, however, 168 * not make any changes. 169 * @return boolean; whether the internal storage is a wrapped pointer to the original collection 170 */ 171 boolean isWrap(); 172 173 /** 174 * Return whether the internal storage is a (shallow) copy of the original collection. If true, this means that anyone 175 * holding a pointer to the original of the data structure can not change it anymore. Nor can the users of the 176 * ImmutableCollection itself make any changes. 177 * @return boolean; whether the internal storage is a safe copy of the original collection 178 */ 179 default boolean isCopy() 180 { 181 return !isWrap(); 182 } 183 184 }