diff --git a/src/builder/java/speiger/src/builder/GlobalVariables.java b/src/builder/java/speiger/src/builder/GlobalVariables.java index 3c724d9a..edc3cbb2 100644 --- a/src/builder/java/speiger/src/builder/GlobalVariables.java +++ b/src/builder/java/speiger/src/builder/GlobalVariables.java @@ -161,7 +161,7 @@ public class GlobalVariables addClassMapper("SETS", "Sets"); addClassMapper("COLLECTIONS", "Collections"); addClassMapper("ARRAYS", "Arrays"); - addClassMapper("SPLIT_ITERATORS", "SplitIterators"); + addClassMapper("SPLIT_ITERATORS", "Splititerators"); addClassMapper("ITERATORS", "Iterators"); addBiClassMapper("MAPS", "Maps", "2"); @@ -169,6 +169,7 @@ public class GlobalVariables addClassMapper("LIST_ITERATOR", "ListIterator"); addClassMapper("BI_ITERATOR", "BidirectionalIterator"); addBiClassMapper("BI_CONSUMER", "Consumer", ""); + addClassMapper("SPLIT_ITERATOR", "Splititerator"); addClassMapper("ITERATOR", "Iterator"); addClassMapper("ITERABLE", "Iterable"); addClassMapper("COLLECTION", "Collection"); diff --git a/src/builder/java/speiger/src/builder/PrimitiveCollectionsBuilder.java b/src/builder/java/speiger/src/builder/PrimitiveCollectionsBuilder.java index 57cb0e74..5847ef4f 100644 --- a/src/builder/java/speiger/src/builder/PrimitiveCollectionsBuilder.java +++ b/src/builder/java/speiger/src/builder/PrimitiveCollectionsBuilder.java @@ -79,7 +79,7 @@ public class PrimitiveCollectionsBuilder extends TemplateProcessor nameRemapper.put("EnumMap", "Enum2%sMap"); addBlockage(ClassType.OBJECT, "Consumer", "Comparator", "Stack"); addBlockage(ClassType.BOOLEAN, "ArraySet", "AVLTreeSet", "RBTreeSet", "SortedSet", "NavigableSet", "OpenHashSet", "OpenCustomHashSet", "LinkedOpenHashSet", "LinkedOpenCustomHashSet"); - addBlockage(ClassType.BOOLEAN, "SplitIterators", "SortedMap", "NavigableMap", "OpenHashMap", "LinkedOpenHashMap", "OpenCustomHashMap", "LinkedOpenCustomHashMap", "ArrayMap", "RBTreeMap", "AVLTreeMap"); + addBlockage(ClassType.BOOLEAN, "SortedMap", "NavigableMap", "OpenHashMap", "LinkedOpenHashMap", "OpenCustomHashMap", "LinkedOpenCustomHashMap", "ArrayMap", "RBTreeMap", "AVLTreeMap"); } protected void create(ClassType mainType, ClassType subType) diff --git a/src/builder/resources/speiger/assets/collections/templates/collections/Collection.template b/src/builder/resources/speiger/assets/collections/templates/collections/Collection.template index 97e84c1e..e2bf47a9 100644 --- a/src/builder/resources/speiger/assets/collections/templates/collections/Collection.template +++ b/src/builder/resources/speiger/assets/collections/templates/collections/Collection.template @@ -6,16 +6,10 @@ import java.util.Objects; import java.util.function.JAVA_PREDICATE; import java.util.function.Predicate; import java.util.stream.JAVA_STREAM; - -#endif -#if !TYPE_BOOLEAN -#if !PRIMITIVES -import java.util.stream.Stream; -#endif import java.util.stream.StreamSupport; +#endif import speiger.src.collections.PACKAGE.utils.SPLIT_ITERATORS; -#endif #if TYPE_BYTE || TYPE_SHORT || TYPE_CHAR || TYPE_FLOAT import speiger.src.collections.utils.SanityChecks; @@ -187,21 +181,18 @@ public interface COLLECTION KEY_GENERIC_TYPE extends Collection, ITE @Override public ITERATOR KEY_GENERIC_TYPE iterator(); -#if !TYPE_BOOLEAN -#if !TYPE_OBJECT +#if PRIMITIVES /** * Returns a Java-Type-Specific Stream to reduce boxing/unboxing. * @return a Stream of the closest java type */ - default JAVA_STREAM primitiveStream() { return StreamSupport.NEW_STREAM(SPLIT_ITERATORS.createCollectionSplit(this, 0), false); } + default JAVA_STREAM primitiveStream() { return StreamSupport.NEW_STREAM(SPLIT_ITERATORS.createJavaSplititerator(this, 0), false); } -#else +#endif /** - * Returns a Boxed Stream - * @return Stream of the type of collection + * A Type Specific Type Splititerator to reduce boxing/unboxing + * @return type specific splititerator */ @Override - default Stream stream() { return StreamSupport.stream(ObjectSplitIterators.createCollectionSplit(this, 0), false); } -#endif -#endif + default SPLIT_ITERATOR KEY_GENERIC_TYPE spliterator() { return SPLIT_ITERATORS.createSplititerator(this, 0); } } \ No newline at end of file diff --git a/src/builder/resources/speiger/assets/collections/templates/collections/Iterable.template b/src/builder/resources/speiger/assets/collections/templates/collections/Iterable.template index 0984e11e..baaf1956 100644 --- a/src/builder/resources/speiger/assets/collections/templates/collections/Iterable.template +++ b/src/builder/resources/speiger/assets/collections/templates/collections/Iterable.template @@ -6,6 +6,8 @@ import java.util.function.Consumer; import speiger.src.collections.PACKAGE.functions.CONSUMER; #endif +import speiger.src.collections.PACKAGE.collections.SPLIT_ITERATOR; +import speiger.src.collections.PACKAGE.utils.SPLIT_ITERATORS; /** * A Type-Specific {@link Iterable} that reduces (un)boxing @@ -51,4 +53,11 @@ public interface ITERABLE KEY_GENERIC_TYPE extends Iterable iterator().forEachRemaining(action); } #endif -} + + /** + * A Type Specific Type Splititerator to reduce boxing/unboxing + * @return type specific splititerator + */ + @Override + default SPLIT_ITERATOR KEY_GENERIC_TYPE spliterator() { return SPLIT_ITERATORS.createUnknownSplititerator(iterator(), 0); } +} \ No newline at end of file diff --git a/src/builder/resources/speiger/assets/collections/templates/collections/Splititerator.template b/src/builder/resources/speiger/assets/collections/templates/collections/Splititerator.template new file mode 100644 index 00000000..c12ee884 --- /dev/null +++ b/src/builder/resources/speiger/assets/collections/templates/collections/Splititerator.template @@ -0,0 +1,32 @@ +package speiger.src.collections.PACKAGE.collections; + +#if !TYPE_OBJECT +import java.util.Spliterator.OfPrimitive; +#else +import java.util.Spliterator; +#endif +import java.util.function.Consumer; + +#if !TYPE_OBJECT +import speiger.src.collections.PACKAGE.functions.CONSUMER; + +#endif +/** + * A Type Specific Split-Iterator that reduces boxing/unboxing + * It fills the gaps of the java and uses this collection interfaces + * @Type(T) + */ +#if TYPE_OBJECT +public interface SPLIT_ITERATOR KEY_GENERIC_TYPE extends Spliterator KEY_GENERIC_TYPE, ITERATOR KEY_GENERIC_TYPE +#else +public interface SPLIT_ITERATOR KEY_GENERIC_TYPE extends OfPrimitive, ITERATOR KEY_GENERIC_TYPE +#endif +{ +#if !TYPE_OBJECT + @Override + default void forEachRemaining(CONSUMER KEY_GENERIC_TYPE action) { ITERATOR.super.forEachRemaining(action); } +#endif + @Override + @Primitive + default void forEachRemaining(Consumer action) { ITERATOR.super.forEachRemaining(action); } +} \ No newline at end of file diff --git a/src/builder/resources/speiger/assets/collections/templates/lists/ArrayList.template b/src/builder/resources/speiger/assets/collections/templates/lists/ArrayList.template index 71ad6406..b12af838 100644 --- a/src/builder/resources/speiger/assets/collections/templates/lists/ArrayList.template +++ b/src/builder/resources/speiger/assets/collections/templates/lists/ArrayList.template @@ -33,7 +33,13 @@ import speiger.src.collections.utils.Stack; #else import speiger.src.collections.objects.utils.ObjectArrays; #endif +#if PRIMITIVES +import java.util.stream.JAVA_STREAM; +import java.util.stream.StreamSupport; +#endif import speiger.src.collections.PACKAGE.utils.IARRAY; +import speiger.src.collections.PACKAGE.collections.SPLIT_ITERATOR; +import speiger.src.collections.PACKAGE.utils.SPLIT_ITERATORS; import speiger.src.collections.utils.SanityChecks; #if TYPE_OBJECT @@ -941,4 +947,22 @@ public class ARRAY_LIST KEY_GENERIC_TYPE extends ABSTRACT_LIST KEY_GENERIC_TYPE if (index < 0 || index > size) throw new IndexOutOfBoundsException("Index: " + index + ", Size: " + size); } + +#if PRIMITIVES + /** + * Returns a Java-Type-Specific Stream to reduce boxing/unboxing. + * @return a Stream of the closest java type + * @note characteristics are ordered, sized, subsized + */ + @Override + public JAVA_STREAM primitiveStream() { return StreamSupport.NEW_STREAM(SPLIT_ITERATORS.createArrayJavaSplititerator(data, size, 16464), false); } + +#endif + /** + * A Type Specific Type Splititerator to reduce boxing/unboxing + * @return type specific splititerator + * @note characteristics are ordered, sized, subsized + */ + @Override + public SPLIT_ITERATOR KEY_GENERIC_TYPE spliterator() { return SPLIT_ITERATORS.createArraySplititerator(data, size, 16464); } } \ No newline at end of file diff --git a/src/builder/resources/speiger/assets/collections/templates/lists/List.template b/src/builder/resources/speiger/assets/collections/templates/lists/List.template index ad2ae33f..7c2a44f9 100644 --- a/src/builder/resources/speiger/assets/collections/templates/lists/List.template +++ b/src/builder/resources/speiger/assets/collections/templates/lists/List.template @@ -12,10 +12,12 @@ import java.util.function.UnaryOperator; import java.util.Comparator; import speiger.src.collections.PACKAGE.collections.COLLECTION; +import speiger.src.collections.PACKAGE.collections.SPLIT_ITERATOR; #if !TYPE_OBJECT import speiger.src.collections.PACKAGE.functions.COMPARATOR; #endif import speiger.src.collections.PACKAGE.utils.ARRAYS; +import speiger.src.collections.PACKAGE.utils.SPLIT_ITERATORS; #if TYPE_BYTE || TYPE_SHORT || TYPE_CHAR || TYPE_FLOAT import speiger.src.collections.utils.SanityChecks; #endif @@ -437,4 +439,10 @@ public interface LIST KEY_GENERIC_TYPE extends COLLECTION KEY_GENERIC_TYPE, List } #endif #endif + /** + * A Type Specific Type Splititerator to reduce boxing/unboxing + * @return type specific splititerator + */ + @Override + default SPLIT_ITERATOR KEY_GENERIC_TYPE spliterator() { return SPLIT_ITERATORS.createSplititerator(this, 0); } } \ No newline at end of file diff --git a/src/builder/resources/speiger/assets/collections/templates/sets/NavigableSet.template b/src/builder/resources/speiger/assets/collections/templates/sets/NavigableSet.template index 39afc093..6d77bc30 100644 --- a/src/builder/resources/speiger/assets/collections/templates/sets/NavigableSet.template +++ b/src/builder/resources/speiger/assets/collections/templates/sets/NavigableSet.template @@ -3,6 +3,8 @@ package speiger.src.collections.PACKAGE.sets; import java.util.NavigableSet; import speiger.src.collections.PACKAGE.collections.BI_ITERATOR; +import speiger.src.collections.PACKAGE.collections.SPLIT_ITERATOR; +import speiger.src.collections.PACKAGE.utils.SPLIT_ITERATORS; /** * A Type Specific Navigable Set interface with a couple helper methods @@ -114,6 +116,13 @@ public interface NAVIGABLE_SET KEY_GENERIC_TYPE extends NavigableSet @Override public NAVIGABLE_SET KEY_GENERIC_TYPE descendingSet(); + /** + * A Type Specific Type Splititerator to reduce boxing/unboxing + * @return type specific splititerator + */ + @Override + default SPLIT_ITERATOR KEY_GENERIC_TYPE spliterator() { return SPLIT_ITERATORS.createSplititerator(this, 0); } + #if !TYPE_OBJECT @Override @Deprecated @@ -158,5 +167,6 @@ public interface NAVIGABLE_SET KEY_GENERIC_TYPE extends NavigableSet @Override @Deprecated public default SORTED_SET KEY_GENERIC_TYPE tailSet(CLASS_TYPE fromElement) { return SORTED_SET.super.tailSet(fromElement); } + #endif } \ No newline at end of file diff --git a/src/builder/resources/speiger/assets/collections/templates/sets/Set.template b/src/builder/resources/speiger/assets/collections/templates/sets/Set.template index a71b2f51..5fca2af1 100644 --- a/src/builder/resources/speiger/assets/collections/templates/sets/Set.template +++ b/src/builder/resources/speiger/assets/collections/templates/sets/Set.template @@ -4,6 +4,8 @@ import java.util.Set; import speiger.src.collections.PACKAGE.collections.COLLECTION; import speiger.src.collections.PACKAGE.collections.ITERATOR; +import speiger.src.collections.PACKAGE.collections.SPLIT_ITERATOR; +import speiger.src.collections.PACKAGE.utils.SPLIT_ITERATORS; /** * A Type Specific Set class to reduce boxing/unboxing @@ -45,4 +47,10 @@ public interface SET KEY_GENERIC_TYPE extends Set, COLLECTION KEY_GE return COLLECTION.super.remove(o); } #endif + /** + * A Type Specific Type Splititerator to reduce boxing/unboxing + * @return type specific splititerator + */ + @Override + default SPLIT_ITERATOR KEY_GENERIC_TYPE spliterator() { return SPLIT_ITERATORS.createSplititerator(this, 0); } } \ No newline at end of file diff --git a/src/builder/resources/speiger/assets/collections/templates/sets/SortedSet.template b/src/builder/resources/speiger/assets/collections/templates/sets/SortedSet.template index 6f98494f..76d40a86 100644 --- a/src/builder/resources/speiger/assets/collections/templates/sets/SortedSet.template +++ b/src/builder/resources/speiger/assets/collections/templates/sets/SortedSet.template @@ -3,11 +3,13 @@ package speiger.src.collections.PACKAGE.sets; import java.util.SortedSet; import speiger.src.collections.PACKAGE.collections.BI_ITERATOR; +import speiger.src.collections.PACKAGE.collections.SPLIT_ITERATOR; #if TYPE_OBJECT import java.util.Comparator; #else import speiger.src.collections.PACKAGE.functions.COMPARATOR; #endif +import speiger.src.collections.PACKAGE.utils.SPLIT_ITERATORS; /** * A Type Specific SortedSet implementation to reduce boxing/unboxing @@ -68,6 +70,13 @@ public interface SORTED_SET KEY_GENERIC_TYPE extends SET KEY_GENERIC_TYPE, Sorte */ public BI_ITERATOR KEY_GENERIC_TYPE iterator(KEY_TYPE fromElement); + /** + * A Type Specific Type Splititerator to reduce boxing/unboxing + * @return type specific splititerator + */ + @Override + default SPLIT_ITERATOR KEY_GENERIC_TYPE spliterator() { return SPLIT_ITERATORS.createSplititerator(this, 0); } + #if !TYPE_OBJECT /** * A Type Specific SubSet method to reduce boxing/unboxing diff --git a/src/builder/resources/speiger/assets/collections/templates/utils/SplitIterators.template b/src/builder/resources/speiger/assets/collections/templates/utils/SplitIterators.template deleted file mode 100644 index c59dc013..00000000 --- a/src/builder/resources/speiger/assets/collections/templates/utils/SplitIterators.template +++ /dev/null @@ -1,282 +0,0 @@ -package speiger.src.collections.PACKAGE.utils; - -import java.util.Comparator; -import java.util.Spliterator; -#if PRIMITIVES -import java.util.Spliterator.JAVA_SPLIT_ITERATOR; -#else -import java.util.function.Consumer; -#endif - -import speiger.src.collections.PACKAGE.collections.COLLECTION; -import speiger.src.collections.PACKAGE.collections.ITERATOR; -import speiger.src.collections.utils.SanityChecks; - -/** - * Helper class that provides SplitIterators for normal and stream usage - */ -public class SPLIT_ITERATORS -{ - /** - * Creates A stream compatible split iterator without copying the original array or boxing - * @param array that should be wrapped into a split iterator - * @param characteristics characteristics properties of this spliterator's source or elements. - * @Type(T) - * @return a split iterator of a Stream compatible type - */ - public static GENERIC_KEY_BRACES JAVA_SPLIT_ITERATOR KEY_GENERIC_TYPE createArraySplit(KEY_TYPE[] array, int characteristics) { return createArraySplit(array, 0, array.length, characteristics);} - /** - * Creates A stream compatible split iterator without copying the original array or boxing - * @param array that should be wrapped into a split iterator - * @param size the maximum index within the array - * @param characteristics characteristics properties of this spliterator's source or elements. - * @Type(T) - * @return a split iterator of a Stream compatible type - * @throws IllegalStateException if the size is outside of the array size - */ - public static GENERIC_KEY_BRACES JAVA_SPLIT_ITERATOR KEY_GENERIC_TYPE createArraySplit(KEY_TYPE[] array, int size, int characteristics) { return createArraySplit(array, 0, size, characteristics);} - /** - * Creates A stream compatible split iterator without copying the original array or boxing - * @param array that should be wrapped into a split iterator - * @param offset the starting index of the array - * @param size the maximum index within the array - * @param characteristics characteristics properties of this spliterator's source or elements. - * @Type(T) - * @return a split iterator of a Stream compatible type - * @throws IllegalStateException the offset and size are outside of the arrays range - */ - public static GENERIC_KEY_BRACES JAVA_SPLIT_ITERATOR KEY_GENERIC_TYPE createArraySplit(KEY_TYPE[] array, int offset, int size, int characteristics) { - SanityChecks.checkArrayCapacity(array.length, offset, size); - return new ArraySplitIteratorBRACES(array, offset, size, characteristics); - } - - /** - * Creates a stream compatible split iterator without copying it or boxing it - * @param collection the collection that should be wrapped in a split iterator - * @param characteristics characteristics properties of this spliterator's source or elements. - * @Type(T) - * @return a split iterator of a Stream compatible type - */ - public static GENERIC_KEY_BRACES JAVA_SPLIT_ITERATOR KEY_GENERIC_TYPE createCollectionSplit(COLLECTION KEY_GENERIC_TYPE collection, int characteristics) { - return new IteratorSpliteratorBRACES(collection, characteristics); - } - - /** - * Creates a stream compatible split iterator without copying it or boxing it - * @param iterator the Iterator that should be wrapped in a split iterator - * @param characteristics characteristics properties of this spliterator's source or elements. - * @Type(T) - * @return a split iterator of a Stream compatible type - */ - public static GENERIC_KEY_BRACES JAVA_SPLIT_ITERATOR KEY_GENERIC_TYPE createUnknownIterator(ITERATOR KEY_GENERIC_TYPE iterator, int characteristics) { - return new IteratorSpliteratorBRACES(iterator, characteristics); - } - - /** - * Creates a stream compatible split iterator without copying it or boxing it - * @param iterator the collection that should be wrapped in a split iterator - * @param size the amount of elements in the iterator - * @param characteristics characteristics properties of this spliterator's source or elements. - * @Type(T) - * @return a split iterator of a Stream compatible type - */ - public static GENERIC_KEY_BRACES JAVA_SPLIT_ITERATOR KEY_GENERIC_TYPE createSizedIterator(ITERATOR KEY_GENERIC_TYPE iterator, long size, int characteristics) { - return new IteratorSpliteratorBRACES(iterator, size, characteristics); - } - - static class IteratorSpliterator KEY_GENERIC_TYPE implements JAVA_SPLIT_ITERATOR KEY_GENERIC_TYPE { - static final int BATCH_UNIT = 1 << 10; - static final int MAX_BATCH = 1 << 25; - private final COLLECTION KEY_GENERIC_TYPE collection; - private ITERATOR KEY_GENERIC_TYPE it; - private final int characteristics; - private long est; - private int batch; - - IteratorSpliterator(COLLECTION KEY_GENERIC_TYPE collection, int characteristics) { - this.collection = collection; - it = null; - this.characteristics = (characteristics & Spliterator.CONCURRENT) == 0 - ? characteristics | Spliterator.SIZED | Spliterator.SUBSIZED - : characteristics; - } - - IteratorSpliterator(ITERATOR KEY_GENERIC_TYPE iterator, long size, int characteristics) { - collection = null; - it = iterator; - est = size; - this.characteristics = (characteristics & Spliterator.CONCURRENT) == 0 - ? characteristics | Spliterator.SIZED | Spliterator.SUBSIZED - : characteristics; - } - - IteratorSpliterator(ITERATOR KEY_GENERIC_TYPE iterator, int characteristics) { - collection = null; - it = iterator; - est = Long.MAX_VALUE; - this.characteristics = characteristics & ~(Spliterator.SIZED | Spliterator.SUBSIZED); - } - - private ITERATOR KEY_GENERIC_TYPE iterator() - { - if (it == null) { - it = collection.iterator(); - est = collection.size(); - } - return it; - } - - @Override - public JAVA_SPLIT_ITERATOR KEY_GENERIC_TYPE trySplit() { - ITERATOR KEY_GENERIC_TYPE i = iterator(); - if (est > 1 && i.hasNext()) { - int n = Math.min(batch + BATCH_UNIT, Math.min((int)est, MAX_BATCH)); - KEY_TYPE[] a = NEW_KEY_ARRAY(n); - int j = 0; - do { a[j] = i.NEXT(); } while (++j < n && i.hasNext()); - batch = j; - if (est != Long.MAX_VALUE) - est -= j; - return new ArraySplitIteratorBRACES(a, 0, j, characteristics); - } - return null; - } - -#if TYPE_OBJECT - @Override - public void forEachRemaining(Consumer action) { - if (action == null) throw new NullPointerException(); - iterator().forEachRemaining(action); - } - - @Override - public boolean tryAdvance(Consumer action) { - if (action == null) throw new NullPointerException(); - ITERATOR KEY_GENERIC_TYPE iter = iterator(); - if (iter.hasNext()) { - action.accept(iter.NEXT()); - return true; - } - return false; - } - -#else - @Override - public void forEachRemaining(JAVA_CONSUMER action) { - if (action == null) throw new NullPointerException(); - iterator().forEachRemaining(T -> action.accept(T)); - } - - @Override - public boolean tryAdvance(JAVA_CONSUMER action) { - if (action == null) throw new NullPointerException(); - ITERATOR KEY_GENERIC_TYPE iter = iterator(); - if (iter.hasNext()) { - action.accept(iter.NEXT()); - return true; - } - return false; - } - -#endif - @Override - public long estimateSize() { - iterator(); - return est; - } - - @Override - public int characteristics() { return characteristics; } - - @Override -#if TYPE_OBJECT - public Comparator getComparator() { -#else - public Comparator getComparator() { -#endif - if (hasCharacteristics(4)) //Sorted - return null; - throw new IllegalStateException(); - } - } - - static final class ArraySplitIterator KEY_GENERIC_TYPE implements JAVA_SPLIT_ITERATOR KEY_GENERIC_TYPE { - private final KEY_TYPE[] array; - private int index; - private final int fence; - private final int characteristics; - - public ArraySplitIterator(KEY_TYPE[] array, int origin, int fence, int additionalCharacteristics) { - this.array = array; - index = origin; - this.fence = fence; - characteristics = additionalCharacteristics | Spliterator.SIZED | Spliterator.SUBSIZED; - } - - @Override - public JAVA_SPLIT_ITERATOR KEY_GENERIC_TYPE trySplit() { - int lo = index, mid = (lo + fence) >>> 1; - return (lo >= mid) ? null : new ArraySplitIteratorBRACES(array, lo, index = mid, characteristics); - } - -#if TYPE_OBJECT - @Override - public void forEachRemaining(Consumer action) { - if (action == null) throw new NullPointerException(); - T[] a; int i, hi; - if ((a = array).length >= (hi = fence) && (i = index) >= 0 && i < (index = hi)) { - do { action.accept(a[i]); } while (++i < hi); - } - } - - @Override - public boolean tryAdvance(Consumer action) { - if (action == null) throw new NullPointerException(); - if (index >= 0 && index < fence) { - action.accept(array[index++]); - return true; - } - return false; - } - -#else - @Override - public void forEachRemaining(JAVA_CONSUMER action) { - if (action == null) throw new NullPointerException(); - KEY_TYPE[] a; int i, hi; - if ((a = array).length >= (hi = fence) && (i = index) >= 0 && i < (index = hi)) { - do { action.accept(a[i]); } while (++i < hi); - } - } - - @Override - public boolean tryAdvance(JAVA_CONSUMER action) { - if (action == null) throw new NullPointerException(); - if (index >= 0 && index < fence) { - action.accept(array[index++]); - return true; - } - return false; - } - -#endif - @Override - public long estimateSize() { return fence - index; } - - @Override - public int characteristics() { - return characteristics; - } - - @Override -#if TYPE_OBJECT - public Comparator getComparator() { -#else - public Comparator getComparator() { -#endif - if (hasCharacteristics(4)) //Sorted - return null; - throw new IllegalStateException(); - } - } -} diff --git a/src/builder/resources/speiger/assets/collections/templates/utils/Splititerators.template b/src/builder/resources/speiger/assets/collections/templates/utils/Splititerators.template new file mode 100644 index 00000000..8be299fc --- /dev/null +++ b/src/builder/resources/speiger/assets/collections/templates/utils/Splititerators.template @@ -0,0 +1,480 @@ +package speiger.src.collections.PACKAGE.utils; + +import java.util.Comparator; +import java.util.Spliterator; +#if PRIMITIVES +import java.util.Spliterator.JAVA_SPLIT_ITERATOR; +#endif +import java.util.function.Consumer; + +import speiger.src.collections.PACKAGE.collections.COLLECTION; +import speiger.src.collections.PACKAGE.collections.ITERATOR; +import speiger.src.collections.PACKAGE.collections.SPLIT_ITERATOR; +#if !TYPE_OBJECT +import speiger.src.collections.PACKAGE.functions.CONSUMER; +#endif +import speiger.src.collections.utils.SanityChecks; + +/** + * Helper class that provides SplitIterators for normal and stream usage + */ +public class SPLIT_ITERATORS +{ +#if PRIMITIVES + /** + * Creates A stream compatible split iterator without copying the original array or boxing + * @param array that should be wrapped into a split iterator + * @param characteristics characteristics properties of this spliterator's source or elements. + * @Type(T) + * @return a split iterator of a Stream compatible type + */ + public static GENERIC_KEY_BRACES JAVA_SPLIT_ITERATOR KEY_GENERIC_TYPE createArrayJavaSplititerator(KEY_TYPE[] array, int characteristics) { return createArrayJavaSplititerator(array, 0, array.length, characteristics);} + /** + * Creates A stream compatible split iterator without copying the original array or boxing + * @param array that should be wrapped into a split iterator + * @param size the maximum index within the array + * @param characteristics characteristics properties of this spliterator's source or elements. + * @Type(T) + * @return a split iterator of a Stream compatible type + * @throws IllegalStateException if the size is outside of the array size + */ + public static GENERIC_KEY_BRACES JAVA_SPLIT_ITERATOR KEY_GENERIC_TYPE createArrayJavaSplititerator(KEY_TYPE[] array, int size, int characteristics) { return createArrayJavaSplititerator(array, 0, size, characteristics);} + /** + * Creates A stream compatible split iterator without copying the original array or boxing + * @param array that should be wrapped into a split iterator + * @param offset the starting index of the array + * @param size the maximum index within the array + * @param characteristics characteristics properties of this spliterator's source or elements. + * @Type(T) + * @return a split iterator of a Stream compatible type + * @throws IllegalStateException the offset and size are outside of the arrays range + */ + public static GENERIC_KEY_BRACES JAVA_SPLIT_ITERATOR KEY_GENERIC_TYPE createArrayJavaSplititerator(KEY_TYPE[] array, int offset, int size, int characteristics) { + SanityChecks.checkArrayCapacity(array.length, offset, size); + return new ArraySplitIteratorBRACES(array, offset, size, characteristics); + } + + /** + * Creates a stream compatible split iterator without copying it or boxing it + * @param collection the collection that should be wrapped in a split iterator + * @param characteristics characteristics properties of this spliterator's source or elements. + * @Type(T) + * @return a split iterator of a Stream compatible type + */ + public static GENERIC_KEY_BRACES JAVA_SPLIT_ITERATOR KEY_GENERIC_TYPE createJavaSplititerator(COLLECTION KEY_GENERIC_TYPE collection, int characteristics) { + return new IteratorSpliteratorBRACES(collection, characteristics); + } + + /** + * Creates a stream compatible split iterator without copying it or boxing it + * @param iterator the Iterator that should be wrapped in a split iterator + * @param characteristics characteristics properties of this spliterator's source or elements. + * @Type(T) + * @return a split iterator of a Stream compatible type + */ + public static GENERIC_KEY_BRACES JAVA_SPLIT_ITERATOR KEY_GENERIC_TYPE createUnknownJavaSplititerator(ITERATOR KEY_GENERIC_TYPE iterator, int characteristics) { + return new IteratorSpliteratorBRACES(iterator, characteristics); + } + + /** + * Creates a stream compatible split iterator without copying it or boxing it + * @param iterator the collection that should be wrapped in a split iterator + * @param size the amount of elements in the iterator + * @param characteristics characteristics properties of this spliterator's source or elements. + * @Type(T) + * @return a split iterator of a Stream compatible type + */ + public static GENERIC_KEY_BRACES JAVA_SPLIT_ITERATOR KEY_GENERIC_TYPE createSizedJavaSplititerator(ITERATOR KEY_GENERIC_TYPE iterator, long size, int characteristics) { + return new IteratorSpliteratorBRACES(iterator, size, characteristics); + } + +#endif + /** + * Creates a Type Specific SplitIterator to reduce boxing/unboxing + * @param array that should be wrapped into a split iterator + * @param characteristics characteristics properties of this spliterator's source or elements. + * @Type(T) + * @return a Type Specific SplitIterator + */ + public static GENERIC_KEY_BRACES SPLIT_ITERATOR KEY_GENERIC_TYPE createArraySplititerator(KEY_TYPE[] array, int characteristics) { return createArraySplititerator(array, 0, array.length, characteristics);} + /** + * Creates a Type Specific SplitIterator to reduce boxing/unboxing + * @param array that should be wrapped into a split iterator + * @param size the maximum index within the array + * @param characteristics characteristics properties of this spliterator's source or elements. + * @Type(T) + * @return a Type Specific SplitIterator + * @throws IllegalStateException if the size is outside of the array size + */ + public static GENERIC_KEY_BRACES SPLIT_ITERATOR KEY_GENERIC_TYPE createArraySplititerator(KEY_TYPE[] array, int size, int characteristics) { return createArraySplititerator(array, 0, size, characteristics);} + /** + * Creates a Type Specific SplitIterator to reduce boxing/unboxing + * @param array that should be wrapped into a split iterator + * @param offset the starting index of the array + * @param size the maximum index within the array + * @param characteristics characteristics properties of this spliterator's source or elements. + * @Type(T) + * @return a Type Specific SplitIterator + * @throws IllegalStateException the offset and size are outside of the arrays range + */ + public static GENERIC_KEY_BRACES SPLIT_ITERATOR KEY_GENERIC_TYPE createArraySplititerator(KEY_TYPE[] array, int offset, int size, int characteristics) { + SanityChecks.checkArrayCapacity(array.length, offset, size); + return new TypeArraySplitIteratorBRACES(array, offset, size, characteristics); + } + + /** + * Creates a Type Specific SplitIterator to reduce boxing/unboxing + * @param collection the collection that should be wrapped in a split iterator + * @param characteristics characteristics properties of this spliterator's source or elements. + * @Type(T) + * @return a Type Specific SplitIterator + */ + public static GENERIC_KEY_BRACES SPLIT_ITERATOR KEY_GENERIC_TYPE createSplititerator(COLLECTION KEY_GENERIC_TYPE collection, int characteristics) { + return new TypeIteratorSpliteratorBRACES(collection, characteristics); + } + + /** + * Creates a Type Specific SplitIterator to reduce boxing/unboxing + * @param iterator the Iterator that should be wrapped in a split iterator + * @param characteristics characteristics properties of this spliterator's source or elements. + * @Type(T) + * @return a Type Specific SplitIterator + */ + public static GENERIC_KEY_BRACES SPLIT_ITERATOR KEY_GENERIC_TYPE createUnknownSplititerator(ITERATOR KEY_GENERIC_TYPE iterator, int characteristics) { + return new TypeIteratorSpliteratorBRACES(iterator, characteristics); + } + + /** + * Creates a Type Specific SplitIterator to reduce boxing/unboxing + * @param iterator the collection that should be wrapped in a split iterator + * @param size the amount of elements in the iterator + * @param characteristics characteristics properties of this spliterator's source or elements. + * @Type(T) + * @return a Type Specific SplitIterator + */ + public static GENERIC_KEY_BRACES SPLIT_ITERATOR KEY_GENERIC_TYPE createSizedSplititerator(ITERATOR KEY_GENERIC_TYPE iterator, long size, int characteristics) { + return new TypeIteratorSpliteratorBRACES(iterator, size, characteristics); + } + + static class TypeIteratorSpliterator KEY_GENERIC_TYPE implements SPLIT_ITERATOR KEY_GENERIC_TYPE { + static final int BATCH_UNIT = 1 << 10; + static final int MAX_BATCH = 1 << 25; + private final COLLECTION KEY_GENERIC_TYPE collection; + private ITERATOR KEY_GENERIC_TYPE it; + private final int characteristics; + private long est; + private int batch; + + TypeIteratorSpliterator(COLLECTION KEY_GENERIC_TYPE collection, int characteristics) { + this.collection = collection; + it = null; + this.characteristics = (characteristics & Spliterator.CONCURRENT) == 0 + ? characteristics | Spliterator.SIZED | Spliterator.SUBSIZED + : characteristics; + } + + TypeIteratorSpliterator(ITERATOR KEY_GENERIC_TYPE iterator, long size, int characteristics) { + collection = null; + it = iterator; + est = size; + this.characteristics = (characteristics & Spliterator.CONCURRENT) == 0 + ? characteristics | Spliterator.SIZED | Spliterator.SUBSIZED + : characteristics; + } + + TypeIteratorSpliterator(ITERATOR KEY_GENERIC_TYPE iterator, int characteristics) { + collection = null; + it = iterator; + est = Long.MAX_VALUE; + this.characteristics = characteristics & ~(Spliterator.SIZED | Spliterator.SUBSIZED); + } + + private ITERATOR KEY_GENERIC_TYPE iterator() + { + if (it == null) { + it = collection.iterator(); + est = collection.size(); + } + return it; + } + + @Override + public SPLIT_ITERATOR KEY_GENERIC_TYPE trySplit() { + ITERATOR KEY_GENERIC_TYPE i = iterator(); + if (est > 1 && i.hasNext()) { + int n = Math.min(batch + BATCH_UNIT, Math.min((int)est, MAX_BATCH)); + KEY_TYPE[] a = NEW_KEY_ARRAY(n); + int j = 0; + do { a[j] = i.NEXT(); } while (++j < n && i.hasNext()); + batch = j; + if (est != Long.MAX_VALUE) + est -= j; + return new TypeArraySplitIteratorBRACES(a, 0, j, characteristics); + } + return null; + } + + @Override + public void forEachRemaining(CONSUMER KEY_SUPER_GENERIC_TYPE action) { + if (action == null) throw new NullPointerException(); + iterator().forEachRemaining(action); + } + +#if !TYPE_OBJECT + @Override + public boolean tryAdvance(CONSUMER KEY_GENERIC_TYPE action) { + if (action == null) throw new NullPointerException(); + ITERATOR KEY_GENERIC_TYPE iter = iterator(); + if (iter.hasNext()) { + action.accept(iter.NEXT()); + return true; + } + return false; + } + +#endif + @Override + public boolean tryAdvance(Consumer action) { + if (action == null) throw new NullPointerException(); + ITERATOR KEY_GENERIC_TYPE iter = iterator(); + if (iter.hasNext()) { + action.accept(KEY_TO_OBJ(iter.NEXT())); + return true; + } + return false; + } + + @Override + public long estimateSize() { + iterator(); + return est; + } + + @Override + public int characteristics() { return characteristics; } + + @Override + public Comparator getComparator() { + if (hasCharacteristics(4)) //Sorted + return null; + throw new IllegalStateException(); + } + + @Override + public KEY_TYPE NEXT() { return iterator().NEXT(); } + + @Override + public boolean hasNext() { return iterator().hasNext(); } + } + + static final class TypeArraySplitIterator KEY_GENERIC_TYPE implements SPLIT_ITERATOR KEY_GENERIC_TYPE { + private final KEY_TYPE[] array; + private int index; + private final int fence; + private final int characteristics; + + public TypeArraySplitIterator(KEY_TYPE[] array, int origin, int fence, int additionalCharacteristics) { + this.array = array; + index = origin; + this.fence = fence; + characteristics = additionalCharacteristics | Spliterator.SIZED | Spliterator.SUBSIZED; + } + + @Override + public SPLIT_ITERATOR KEY_GENERIC_TYPE trySplit() { + int lo = index, mid = (lo + fence) >>> 1; + return (lo >= mid) ? null : new TypeArraySplitIteratorBRACES(array, lo, index = mid, characteristics); + } + + @Override + public void forEachRemaining(CONSUMER KEY_SUPER_GENERIC_TYPE action) { + if (action == null) throw new NullPointerException(); + KEY_TYPE[] a; int i, hi; + if ((a = array).length >= (hi = fence) && (i = index) >= 0 && i < (index = hi)) { + do { action.accept(a[i]); } while (++i < hi); + } + } + +#if !TYPE_OBJECT + @Override + public boolean tryAdvance(CONSUMER KEY_GENERIC_TYPE action) { + if (action == null) throw new NullPointerException(); + if (index >= 0 && index < fence) { + action.accept(array[index++]); + return true; + } + return false; + } + +#endif + @Override + public boolean tryAdvance(Consumer action) { + if (action == null) throw new NullPointerException(); + if (index >= 0 && index < fence) { + action.accept(KEY_TO_OBJ(array[index++])); + return true; + } + return false; + } + + @Override + public long estimateSize() { return fence - index; } + @Override + public int characteristics() { return characteristics; } + @Override + public Comparator getComparator() { + if (hasCharacteristics(4)) //Sorted + return null; + throw new IllegalStateException(); + } + + @Override + public KEY_TYPE NEXT() { return array[index++]; } + @Override + public boolean hasNext() { return index < fence; } + } + +#if PRIMITIVES + static class IteratorSpliterator KEY_GENERIC_TYPE implements JAVA_SPLIT_ITERATOR KEY_GENERIC_TYPE { + static final int BATCH_UNIT = 1 << 10; + static final int MAX_BATCH = 1 << 25; + private final COLLECTION KEY_GENERIC_TYPE collection; + private ITERATOR KEY_GENERIC_TYPE it; + private final int characteristics; + private long est; + private int batch; + + IteratorSpliterator(COLLECTION KEY_GENERIC_TYPE collection, int characteristics) { + this.collection = collection; + it = null; + this.characteristics = (characteristics & Spliterator.CONCURRENT) == 0 + ? characteristics | Spliterator.SIZED | Spliterator.SUBSIZED + : characteristics; + } + + IteratorSpliterator(ITERATOR KEY_GENERIC_TYPE iterator, long size, int characteristics) { + collection = null; + it = iterator; + est = size; + this.characteristics = (characteristics & Spliterator.CONCURRENT) == 0 + ? characteristics | Spliterator.SIZED | Spliterator.SUBSIZED + : characteristics; + } + + IteratorSpliterator(ITERATOR KEY_GENERIC_TYPE iterator, int characteristics) { + collection = null; + it = iterator; + est = Long.MAX_VALUE; + this.characteristics = characteristics & ~(Spliterator.SIZED | Spliterator.SUBSIZED); + } + + private ITERATOR KEY_GENERIC_TYPE iterator() + { + if (it == null) { + it = collection.iterator(); + est = collection.size(); + } + return it; + } + + @Override + public JAVA_SPLIT_ITERATOR KEY_GENERIC_TYPE trySplit() { + ITERATOR KEY_GENERIC_TYPE i = iterator(); + if (est > 1 && i.hasNext()) { + int n = Math.min(batch + BATCH_UNIT, Math.min((int)est, MAX_BATCH)); + KEY_TYPE[] a = NEW_KEY_ARRAY(n); + int j = 0; + do { a[j] = i.NEXT(); } while (++j < n && i.hasNext()); + batch = j; + if (est != Long.MAX_VALUE) + est -= j; + return new ArraySplitIteratorBRACES(a, 0, j, characteristics); + } + return null; + } + + @Override + public void forEachRemaining(JAVA_CONSUMER action) { + if (action == null) throw new NullPointerException(); + iterator().forEachRemaining(T -> action.accept(T)); + } + + @Override + public boolean tryAdvance(JAVA_CONSUMER action) { + if (action == null) throw new NullPointerException(); + ITERATOR KEY_GENERIC_TYPE iter = iterator(); + if (iter.hasNext()) { + action.accept(iter.NEXT()); + return true; + } + return false; + } + + @Override + public long estimateSize() { + iterator(); + return est; + } + + @Override + public int characteristics() { return characteristics; } + + @Override + public Comparator getComparator() { + if (hasCharacteristics(4)) //Sorted + return null; + throw new IllegalStateException(); + } + } + + static final class ArraySplitIterator KEY_GENERIC_TYPE implements JAVA_SPLIT_ITERATOR KEY_GENERIC_TYPE { + private final KEY_TYPE[] array; + private int index; + private final int fence; + private final int characteristics; + + public ArraySplitIterator(KEY_TYPE[] array, int origin, int fence, int additionalCharacteristics) { + this.array = array; + index = origin; + this.fence = fence; + characteristics = additionalCharacteristics | Spliterator.SIZED | Spliterator.SUBSIZED; + } + + @Override + public JAVA_SPLIT_ITERATOR KEY_GENERIC_TYPE trySplit() { + int lo = index, mid = (lo + fence) >>> 1; + return (lo >= mid) ? null : new ArraySplitIteratorBRACES(array, lo, index = mid, characteristics); + } + + @Override + public void forEachRemaining(JAVA_CONSUMER action) { + if (action == null) throw new NullPointerException(); + KEY_TYPE[] a; int i, hi; + if ((a = array).length >= (hi = fence) && (i = index) >= 0 && i < (index = hi)) { + do { action.accept(a[i]); } while (++i < hi); + } + } + + @Override + public boolean tryAdvance(JAVA_CONSUMER action) { + if (action == null) throw new NullPointerException(); + if (index >= 0 && index < fence) { + action.accept(array[index++]); + return true; + } + return false; + } + + @Override + public long estimateSize() { return fence - index; } + @Override + public int characteristics() { return characteristics; } + @Override + public Comparator getComparator() { + if (hasCharacteristics(4)) //Sorted + return null; + throw new IllegalStateException(); + } + } +#endif +}