From 8b5e5a75c14bcee6d3312ddcaa68f08ec8feed74 Mon Sep 17 00:00:00 2001 From: Speiger Date: Sat, 4 Jun 2022 21:05:31 +0200 Subject: [PATCH] Fixing bugs found when implementing Bidirectional Iterator unit tests. -Fixed: AbstractList/ImmutableList/ArraySet/ArrayMap skip/back implementation was causing crashes and didn't update the last returned value. -Fixed: ArraySet/ArrayMap previous was not subtracting before returning value. -Fixed: BidirectionalIterator back was calling the object variant instead of the TypeSpecific Variant. -Fixed: TreeSets/Maps Iterator now fully supports backwards Iterating. -Added: Specialized skip/back function to improve speed in ImmutableHashSet/LinkedHashSet/CustomLinkedHashSet --- .../BidirectionalIterator.template | 2 +- .../templates/lists/AbstractList.template | 4 +- .../templates/lists/ImmutableList.template | 2 +- .../LinkedOpenCustomHashMap.template | 15 +- .../maps/impl/hash/LinkedOpenHashMap.template | 15 +- .../immutable/ImmutableOpenHashMap.template | 13 +- .../maps/impl/misc/ArrayMap.template | 23 +-- .../maps/impl/misc/LinkedEnumMap.template | 10 +- .../maps/impl/tree/AVLTreeMap.template | 152 +++++++++++++----- .../maps/impl/tree/RBTreeMap.template | 152 +++++++++++++----- .../maps/interfaces/OrderedMap.template | 7 + .../templates/sets/AVLTreeSet.template | 56 +++++-- .../templates/sets/ArraySet.template | 8 +- .../sets/ImmutableOpenHashSet.template | 28 +++- .../sets/LinkedOpenCustomHashSet.template | 28 +++- .../templates/sets/LinkedOpenHashSet.template | 28 +++- .../templates/sets/RBTreeSet.template | 56 +++++-- .../templates/utils/maps/Maps.template | 78 ++++++++- 18 files changed, 502 insertions(+), 175 deletions(-) diff --git a/src/builder/resources/speiger/assets/collections/templates/collections/BidirectionalIterator.template b/src/builder/resources/speiger/assets/collections/templates/collections/BidirectionalIterator.template index 8509c5cd..73ea018a 100644 --- a/src/builder/resources/speiger/assets/collections/templates/collections/BidirectionalIterator.template +++ b/src/builder/resources/speiger/assets/collections/templates/collections/BidirectionalIterator.template @@ -57,7 +57,7 @@ public interface BI_ITERATOR KEY_GENERIC_TYPE extends ITERATOR KEY_GENERIC_TYPE public default int back(int amount) { if(amount < 0) throw new IllegalStateException("Can't go forward"); int i = 0; - for(;i 0) lastReturned = Math.min(index-1, size()-1); return steps; } @@ -558,6 +559,7 @@ public abstract class ABSTRACT_LIST KEY_GENERIC_TYPE extends ABSTRACT_COLLECTION if(amount < 0) throw new IllegalStateException("Negative Numbers are not allowed"); int steps = Math.min(amount, index); index -= steps; + if(steps > 0) lastReturned = Math.min(index, size()-1); return steps; } } diff --git a/src/builder/resources/speiger/assets/collections/templates/lists/ImmutableList.template b/src/builder/resources/speiger/assets/collections/templates/lists/ImmutableList.template index 62dd7d66..6476bafd 100644 --- a/src/builder/resources/speiger/assets/collections/templates/lists/ImmutableList.template +++ b/src/builder/resources/speiger/assets/collections/templates/lists/ImmutableList.template @@ -556,7 +556,7 @@ public class IMMUTABLE_LIST KEY_GENERIC_TYPE extends ABSTRACT_LIST KEY_GENERIC_T @Override public int skip(int amount) { if(amount < 0) throw new IllegalStateException("Negative Numbers are not allowed"); - int steps = Math.min(amount, (size() - 1) - index); + int steps = Math.min(amount, size() - index); index += steps; return steps; } diff --git a/src/builder/resources/speiger/assets/collections/templates/maps/impl/customHash/LinkedOpenCustomHashMap.template b/src/builder/resources/speiger/assets/collections/templates/maps/impl/customHash/LinkedOpenCustomHashMap.template index 3dbb63d4..83f017f4 100644 --- a/src/builder/resources/speiger/assets/collections/templates/maps/impl/customHash/LinkedOpenCustomHashMap.template +++ b/src/builder/resources/speiger/assets/collections/templates/maps/impl/customHash/LinkedOpenCustomHashMap.template @@ -22,7 +22,6 @@ import speiger.src.collections.PACKAGE.maps.interfaces.MAP; import speiger.src.collections.PACKAGE.maps.interfaces.ORDERED_MAP; import speiger.src.collections.PACKAGE.sets.ABSTRACT_SET; import speiger.src.collections.PACKAGE.sets.ORDERED_SET; -import speiger.src.collections.PACKAGE.sets.SET; import speiger.src.collections.PACKAGE.utils.STRATEGY; import speiger.src.collections.VALUE_PACKAGE.collections.VALUE_ABSTRACT_COLLECTION; import speiger.src.collections.VALUE_PACKAGE.collections.VALUE_COLLECTION; @@ -57,7 +56,7 @@ import speiger.src.collections.objects.functions.function.ObjectObjectUnaryOpera import speiger.src.collections.objects.collections.ObjectBidirectionalIterator; import speiger.src.collections.objects.lists.ObjectListIterator; import speiger.src.collections.objects.sets.AbstractObjectSet; -import speiger.src.collections.objects.sets.ObjectSet; +import speiger.src.collections.objects.sets.ObjectOrderedSet; #endif import speiger.src.collections.utils.HashUtil; @@ -285,7 +284,7 @@ public class LINKED_CUSTOM_HASH_MAP KEY_VALUE_GENERIC_TYPE extends CUSTOM_HASH_M @Override public boolean moveToFirst(KEY_TYPE key) { - if(strategy.equals(FIRST_ENTRY_KEY(), key)) return false; + if(isEmpty() || strategy.equals(FIRST_ENTRY_KEY(), key)) return false; if(strategy.equals(key, EMPTY_KEY_VALUE)) { if(containsNull) { moveToFirstIndex(nullIndex); @@ -307,7 +306,7 @@ public class LINKED_CUSTOM_HASH_MAP KEY_VALUE_GENERIC_TYPE extends CUSTOM_HASH_M @Override public boolean moveToLast(KEY_TYPE key) { - if(strategy.equals(LAST_ENTRY_KEY(), key)) return false; + if(isEmpty() || strategy.equals(LAST_ENTRY_KEY(), key)) return false; if(strategy.equals(key, EMPTY_KEY_VALUE)) { if(containsNull) { moveToLastIndex(nullIndex); @@ -421,15 +420,15 @@ public class LINKED_CUSTOM_HASH_MAP KEY_VALUE_GENERIC_TYPE extends CUSTOM_HASH_M } @Override - public ObjectSet ENTRY_SET() { + public ObjectOrderedSet ENTRY_SET() { if(entrySet == null) entrySet = new MapEntrySet(); - return entrySet; + return (ObjectOrderedSet)entrySet; } @Override - public SET KEY_GENERIC_TYPE keySet() { + public ORDERED_SET KEY_GENERIC_TYPE keySet() { if(keySet == null) keySet = new KeySet(); - return keySet; + return (ORDERED_SET KEY_GENERIC_TYPE)keySet; } @Override diff --git a/src/builder/resources/speiger/assets/collections/templates/maps/impl/hash/LinkedOpenHashMap.template b/src/builder/resources/speiger/assets/collections/templates/maps/impl/hash/LinkedOpenHashMap.template index 5fd99a19..7ff28314 100644 --- a/src/builder/resources/speiger/assets/collections/templates/maps/impl/hash/LinkedOpenHashMap.template +++ b/src/builder/resources/speiger/assets/collections/templates/maps/impl/hash/LinkedOpenHashMap.template @@ -22,7 +22,6 @@ import speiger.src.collections.PACKAGE.maps.interfaces.MAP; import speiger.src.collections.PACKAGE.maps.interfaces.ORDERED_MAP; import speiger.src.collections.PACKAGE.sets.ABSTRACT_SET; import speiger.src.collections.PACKAGE.sets.ORDERED_SET; -import speiger.src.collections.PACKAGE.sets.SET; import speiger.src.collections.VALUE_PACKAGE.collections.VALUE_ABSTRACT_COLLECTION; import speiger.src.collections.VALUE_PACKAGE.collections.VALUE_COLLECTION; import speiger.src.collections.VALUE_PACKAGE.collections.VALUE_ITERATOR; @@ -56,7 +55,7 @@ import speiger.src.collections.objects.functions.function.ObjectObjectUnaryOpera import speiger.src.collections.objects.collections.ObjectBidirectionalIterator; import speiger.src.collections.objects.lists.ObjectListIterator; import speiger.src.collections.objects.sets.AbstractObjectSet; -import speiger.src.collections.objects.sets.ObjectSet; +import speiger.src.collections.objects.sets.ObjectOrderedSet; #endif import speiger.src.collections.utils.HashUtil; @@ -262,7 +261,7 @@ public class LINKED_HASH_MAP KEY_VALUE_GENERIC_TYPE extends HASH_MAP KEY_VALUE_G @Override public boolean moveToFirst(KEY_TYPE key) { - if(KEY_EQUALS(FIRST_ENTRY_KEY(), key)) return false; + if(isEmpty() || KEY_EQUALS(FIRST_ENTRY_KEY(), key)) return false; if(KEY_EQUALS_NULL(key)) { if(containsNull) { moveToFirstIndex(nullIndex); @@ -284,7 +283,7 @@ public class LINKED_HASH_MAP KEY_VALUE_GENERIC_TYPE extends HASH_MAP KEY_VALUE_G @Override public boolean moveToLast(KEY_TYPE key) { - if(KEY_EQUALS(LAST_ENTRY_KEY(), key)) return false; + if(isEmpty() || KEY_EQUALS(LAST_ENTRY_KEY(), key)) return false; if(KEY_EQUALS_NULL(key)) { if(containsNull) { moveToLastIndex(nullIndex); @@ -425,15 +424,15 @@ public class LINKED_HASH_MAP KEY_VALUE_GENERIC_TYPE extends HASH_MAP KEY_VALUE_G } @Override - public ObjectSet ENTRY_SET() { + public ObjectOrderedSet ENTRY_SET() { if(entrySet == null) entrySet = new MapEntrySet(); - return entrySet; + return (ObjectOrderedSet)entrySet; } @Override - public SET KEY_GENERIC_TYPE keySet() { + public ORDERED_SET KEY_GENERIC_TYPE keySet() { if(keySet == null) keySet = new KeySet(); - return keySet; + return (ORDERED_SET KEY_GENERIC_TYPE)keySet; } @Override diff --git a/src/builder/resources/speiger/assets/collections/templates/maps/impl/immutable/ImmutableOpenHashMap.template b/src/builder/resources/speiger/assets/collections/templates/maps/impl/immutable/ImmutableOpenHashMap.template index 68991fa2..11a5754b 100644 --- a/src/builder/resources/speiger/assets/collections/templates/maps/impl/immutable/ImmutableOpenHashMap.template +++ b/src/builder/resources/speiger/assets/collections/templates/maps/impl/immutable/ImmutableOpenHashMap.template @@ -25,7 +25,9 @@ import speiger.src.collections.PACKAGE.lists.LIST_ITERATOR; import speiger.src.collections.PACKAGE.maps.interfaces.ORDERED_MAP; import speiger.src.collections.PACKAGE.maps.abstracts.ABSTRACT_MAP; import speiger.src.collections.PACKAGE.maps.interfaces.MAP; +#if !TYPE_OBJECT import speiger.src.collections.PACKAGE.sets.ORDERED_SET; +#endif import speiger.src.collections.PACKAGE.utils.maps.MAPS; #if !TYPE_OBJECT import speiger.src.collections.PACKAGE.utils.ARRAYS; @@ -47,7 +49,6 @@ import speiger.src.collections.VALUE_PACKAGE.functions.function.VALUE_PREDICATE; #endif #if !TYPE_OBJECT import speiger.src.collections.PACKAGE.sets.ABSTRACT_SET; -import speiger.src.collections.PACKAGE.sets.SET; #endif import speiger.src.collections.VALUE_PACKAGE.collections.VALUE_ABSTRACT_COLLECTION; import speiger.src.collections.VALUE_PACKAGE.collections.VALUE_COLLECTION; @@ -70,7 +71,7 @@ import speiger.src.collections.objects.functions.function.ObjectObjectUnaryOpera import speiger.src.collections.objects.lists.ObjectListIterator; #endif import speiger.src.collections.objects.sets.AbstractObjectSet; -import speiger.src.collections.objects.sets.ObjectSet; +import speiger.src.collections.objects.sets.ObjectOrderedSet; import speiger.src.collections.utils.HashUtil; import speiger.src.collections.utils.SanityChecks; @@ -100,9 +101,9 @@ public class IMMUTABLE_HASH_MAP KEY_VALUE_GENERIC_TYPE extends ABSTRACT_MAP KEY_ /** The Last Index in the Map */ protected int lastIndex = -1; /** EntrySet cache */ - protected transient FastEntrySet KEY_VALUE_GENERIC_TYPE entrySet; + protected transient FastOrderedSet KEY_VALUE_GENERIC_TYPE entrySet; /** KeySet cache */ - protected transient SET KEY_GENERIC_TYPE keySet; + protected transient ORDERED_SET KEY_GENERIC_TYPE keySet; /** Values cache */ protected transient VALUE_COLLECTION VALUE_GENERIC_TYPE valuesC; @@ -429,13 +430,13 @@ public class IMMUTABLE_HASH_MAP KEY_VALUE_GENERIC_TYPE extends ABSTRACT_MAP KEY_ } @Override - public ObjectSet ENTRY_SET() { + public ObjectOrderedSet ENTRY_SET() { if(entrySet == null) entrySet = new MapEntrySet(); return entrySet; } @Override - public SET KEY_GENERIC_TYPE keySet() { + public ORDERED_SET KEY_GENERIC_TYPE keySet() { if(keySet == null) keySet = new KeySet(); return keySet; } diff --git a/src/builder/resources/speiger/assets/collections/templates/maps/impl/misc/ArrayMap.template b/src/builder/resources/speiger/assets/collections/templates/maps/impl/misc/ArrayMap.template index fe991ad6..55630145 100644 --- a/src/builder/resources/speiger/assets/collections/templates/maps/impl/misc/ArrayMap.template +++ b/src/builder/resources/speiger/assets/collections/templates/maps/impl/misc/ArrayMap.template @@ -27,7 +27,6 @@ import speiger.src.collections.PACKAGE.maps.interfaces.MAP; import speiger.src.collections.PACKAGE.maps.interfaces.ORDERED_MAP; import speiger.src.collections.PACKAGE.sets.ABSTRACT_SET; import speiger.src.collections.PACKAGE.sets.ORDERED_SET; -import speiger.src.collections.PACKAGE.sets.SET; import speiger.src.collections.PACKAGE.utils.maps.MAPS; import speiger.src.collections.VALUE_PACKAGE.collections.VALUE_ABSTRACT_COLLECTION; import speiger.src.collections.VALUE_PACKAGE.collections.VALUE_COLLECTION; @@ -90,7 +89,7 @@ public class ARRAY_MAP KEY_VALUE_GENERIC_TYPE extends ABSTRACT_MAP KEY_VALUE_GEN /** Amount of Elements stored in the ArrayMap */ protected int size = 0; /** KeySet cache */ - protected SET KEY_GENERIC_TYPE keySet; + protected ORDERED_SET KEY_GENERIC_TYPE keySet; /** Values cache */ protected VALUE_COLLECTION VALUE_GENERIC_TYPE valuesC; /** EntrySet cache */ @@ -270,7 +269,7 @@ public class ARRAY_MAP KEY_VALUE_GENERIC_TYPE extends ABSTRACT_MAP KEY_VALUE_GEN @Override public boolean moveToLast(KEY_TYPE key) { int index = findIndex(key); - if(index < size-1) { + if(index >= 0 && index < size-1) { moveIndexToLast(index); return true; } @@ -437,7 +436,7 @@ public class ARRAY_MAP KEY_VALUE_GENERIC_TYPE extends ABSTRACT_MAP KEY_VALUE_GEN } @Override - public SET KEY_GENERIC_TYPE keySet() { + public ORDERED_SET KEY_GENERIC_TYPE keySet() { if(keySet == null) keySet = new KeySet(); return keySet; } @@ -1249,7 +1248,9 @@ public class ARRAY_MAP KEY_VALUE_GENERIC_TYPE extends ABSTRACT_MAP KEY_VALUE_GEN @Override public void remove() { super.remove(); - entry.index = -1; + if(entry != null && entry.index != -1) { + entry.index = -1; + } } @Override @@ -1263,6 +1264,7 @@ public class ARRAY_MAP KEY_VALUE_GENERIC_TYPE extends ABSTRACT_MAP KEY_VALUE_GEN public KeyIterator(KEY_TYPE element) { index = findIndex(element); } + @Override public KEY_TYPE PREVIOUS() { return keys[previousEntry()]; @@ -1319,8 +1321,7 @@ public class ARRAY_MAP KEY_VALUE_GENERIC_TYPE extends ABSTRACT_MAP KEY_VALUE_GEN } public void remove() { - if(lastReturned == -1) - throw new IllegalStateException(); + if(lastReturned == -1) throw new IllegalStateException(); removeIndex(lastReturned); if(lastReturned < index) index--; @@ -1329,8 +1330,8 @@ public class ARRAY_MAP KEY_VALUE_GENERIC_TYPE extends ABSTRACT_MAP KEY_VALUE_GEN public int previousEntry() { if(!hasPrevious()) throw new NoSuchElementException(); - lastReturned = index; - return index--; + index--; + return (lastReturned = index); } public int nextEntry() { @@ -1341,8 +1342,9 @@ public class ARRAY_MAP KEY_VALUE_GENERIC_TYPE extends ABSTRACT_MAP KEY_VALUE_GEN public int skip(int amount) { if(amount < 0) throw new IllegalStateException("Negative Numbers are not allowed"); - int steps = Math.min(amount, (size() - 1) - index); + int steps = Math.min(amount, size() - index); index += steps; + if(steps > 0) lastReturned = Math.min(index-1, size()-1); return steps; } @@ -1350,6 +1352,7 @@ public class ARRAY_MAP KEY_VALUE_GENERIC_TYPE extends ABSTRACT_MAP KEY_VALUE_GEN if(amount < 0) throw new IllegalStateException("Negative Numbers are not allowed"); int steps = Math.min(amount, index); index -= steps; + if(steps > 0) lastReturned = Math.min(index, size()-1); return steps; } } diff --git a/src/builder/resources/speiger/assets/collections/templates/maps/impl/misc/LinkedEnumMap.template b/src/builder/resources/speiger/assets/collections/templates/maps/impl/misc/LinkedEnumMap.template index f95147c6..c4af00c1 100644 --- a/src/builder/resources/speiger/assets/collections/templates/maps/impl/misc/LinkedEnumMap.template +++ b/src/builder/resources/speiger/assets/collections/templates/maps/impl/misc/LinkedEnumMap.template @@ -17,7 +17,6 @@ import speiger.src.collections.PACKAGE.maps.interfaces.MAP; import speiger.src.collections.PACKAGE.maps.interfaces.ORDERED_MAP; import speiger.src.collections.PACKAGE.sets.ABSTRACT_SET; import speiger.src.collections.PACKAGE.sets.ORDERED_SET; -import speiger.src.collections.PACKAGE.sets.SET; import speiger.src.collections.VALUE_PACKAGE.collections.VALUE_ABSTRACT_COLLECTION; import speiger.src.collections.VALUE_PACKAGE.collections.VALUE_COLLECTION; import speiger.src.collections.VALUE_PACKAGE.collections.VALUE_ITERATOR; @@ -29,7 +28,6 @@ import speiger.src.collections.VALUE_PACKAGE.lists.VALUE_LIST_ITERATOR; import speiger.src.collections.objects.collections.ObjectBidirectionalIterator; import speiger.src.collections.objects.lists.ObjectListIterator; import speiger.src.collections.objects.sets.AbstractObjectSet; -import speiger.src.collections.objects.sets.ObjectSet; #endif /** @@ -315,15 +313,15 @@ public class LINKED_ENUM_MAP KEY_ENUM_VALUE_GENERIC_TYPE extends ENUM_MAP KEY_VA } @Override - public ObjectSet ENTRY_SET() { + public ObjectOrderedSet ENTRY_SET() { if(entrySet == null) entrySet = new MapEntrySet(); - return entrySet; + return (ObjectOrderedSet)entrySet; } @Override - public SET KEY_GENERIC_TYPE keySet() { + public ORDERED_SET KEY_GENERIC_TYPE keySet() { if(keySet == null) keySet = new KeySet(); - return keySet; + return (ORDERED_SET KEY_GENERIC_TYPE)keySet; } @Override diff --git a/src/builder/resources/speiger/assets/collections/templates/maps/impl/tree/AVLTreeMap.template b/src/builder/resources/speiger/assets/collections/templates/maps/impl/tree/AVLTreeMap.template index b8b03f42..7233cf86 100644 --- a/src/builder/resources/speiger/assets/collections/templates/maps/impl/tree/AVLTreeMap.template +++ b/src/builder/resources/speiger/assets/collections/templates/maps/impl/tree/AVLTreeMap.template @@ -2051,26 +2051,36 @@ public class AVL_TREE_MAP KEY_VALUE_GENERIC_TYPE extends ABSTRACT_MAP KEY_VALUE_ class DecsendingSubEntryIterator extends SubMapEntryIterator implements ObjectBidirectionalIterator { public DecsendingSubEntryIterator(Node KEY_VALUE_GENERIC_TYPE first, Node KEY_VALUE_GENERIC_TYPE forwardFence, Node KEY_VALUE_GENERIC_TYPE backwardFence) { - super(first, forwardFence, backwardFence); + super(first, forwardFence, backwardFence, false); + } + + @Override + protected Node KEY_VALUE_GENERIC_TYPE moveNext(Node KEY_VALUE_GENERIC_TYPE node) { + return node.previous(); + } + + @Override + protected Node KEY_VALUE_GENERIC_TYPE movePrevious(Node KEY_VALUE_GENERIC_TYPE node) { + return node.next(); } @Override public MAP.Entry KEY_VALUE_GENERIC_TYPE previous() { if(!hasPrevious()) throw new NoSuchElementException(); - return nextEntry(); + return previousEntry(); } @Override public MAP.Entry KEY_VALUE_GENERIC_TYPE next() { if(!hasNext()) throw new NoSuchElementException(); - return previousEntry(); + return nextEntry(); } } class AcsendingSubEntryIterator extends SubMapEntryIterator implements ObjectBidirectionalIterator { public AcsendingSubEntryIterator(Node KEY_VALUE_GENERIC_TYPE first, Node KEY_VALUE_GENERIC_TYPE forwardFence, Node KEY_VALUE_GENERIC_TYPE backwardFence) { - super(first, forwardFence, backwardFence); + super(first, forwardFence, backwardFence, true); } @Override @@ -2089,26 +2099,36 @@ public class AVL_TREE_MAP KEY_VALUE_GENERIC_TYPE extends ABSTRACT_MAP KEY_VALUE_ class DecsendingSubKeyIterator extends SubMapEntryIterator implements BI_ITERATOR KEY_GENERIC_TYPE { public DecsendingSubKeyIterator(Node KEY_VALUE_GENERIC_TYPE first, Node KEY_VALUE_GENERIC_TYPE forwardFence, Node KEY_VALUE_GENERIC_TYPE backwardFence) { - super(first, forwardFence, backwardFence); + super(first, forwardFence, backwardFence, false); + } + + @Override + protected Node KEY_VALUE_GENERIC_TYPE moveNext(Node KEY_VALUE_GENERIC_TYPE node) { + return node.previous(); + } + + @Override + protected Node KEY_VALUE_GENERIC_TYPE movePrevious(Node KEY_VALUE_GENERIC_TYPE node) { + return node.next(); } @Override public KEY_TYPE PREVIOUS() { if(!hasPrevious()) throw new NoSuchElementException(); - return nextEntry().key; + return previousEntry().key; } @Override public KEY_TYPE NEXT() { if(!hasNext()) throw new NoSuchElementException(); - return previousEntry().key; + return nextEntry().key; } } class AcsendingSubKeyIterator extends SubMapEntryIterator implements BI_ITERATOR KEY_GENERIC_TYPE { public AcsendingSubKeyIterator(Node KEY_VALUE_GENERIC_TYPE first, Node KEY_VALUE_GENERIC_TYPE forwardFence, Node KEY_VALUE_GENERIC_TYPE backwardFence) { - super(first, forwardFence, backwardFence); + super(first, forwardFence, backwardFence, true); } @Override @@ -2127,7 +2147,7 @@ public class AVL_TREE_MAP KEY_VALUE_GENERIC_TYPE extends ABSTRACT_MAP KEY_VALUE_ class AcsendingSubValueIterator extends SubMapEntryIterator implements VALUE_BI_ITERATOR VALUE_GENERIC_TYPE { public AcsendingSubValueIterator(Node KEY_VALUE_GENERIC_TYPE first, Node KEY_VALUE_GENERIC_TYPE forwardFence, Node KEY_VALUE_GENERIC_TYPE backwardFence) { - super(first, forwardFence, backwardFence); + super(first, forwardFence, backwardFence, true); } @Override @@ -2146,39 +2166,60 @@ public class AVL_TREE_MAP KEY_VALUE_GENERIC_TYPE extends ABSTRACT_MAP KEY_VALUE_ class DecsendingSubValueIterator extends SubMapEntryIterator implements VALUE_BI_ITERATOR VALUE_GENERIC_TYPE { public DecsendingSubValueIterator(Node KEY_VALUE_GENERIC_TYPE first, Node KEY_VALUE_GENERIC_TYPE forwardFence, Node KEY_VALUE_GENERIC_TYPE backwardFence) { - super(first, forwardFence, backwardFence); + super(first, forwardFence, backwardFence, false); + } + + @Override + protected Node KEY_VALUE_GENERIC_TYPE moveNext(Node KEY_VALUE_GENERIC_TYPE node) { + return node.previous(); + } + + @Override + protected Node KEY_VALUE_GENERIC_TYPE movePrevious(Node KEY_VALUE_GENERIC_TYPE node) { + return node.next(); } @Override public VALUE_TYPE VALUE_PREVIOUS() { if(!hasPrevious()) throw new NoSuchElementException(); - return nextEntry().value; + return previousEntry().value; } @Override public VALUE_TYPE VALUE_NEXT() { if(!hasNext()) throw new NoSuchElementException(); - return previousEntry().value; + return nextEntry().value; } } abstract class SubMapEntryIterator { + final boolean isForward; boolean wasForward; Node KEY_VALUE_GENERIC_TYPE lastReturned; Node KEY_VALUE_GENERIC_TYPE next; + Node KEY_VALUE_GENERIC_TYPE previous; boolean unboundForwardFence; boolean unboundBackwardFence; KEY_TYPE forwardFence; KEY_TYPE backwardFence; - public SubMapEntryIterator(Node KEY_VALUE_GENERIC_TYPE first, Node KEY_VALUE_GENERIC_TYPE forwardFence, Node KEY_VALUE_GENERIC_TYPE backwardFence) - { + public SubMapEntryIterator(Node KEY_VALUE_GENERIC_TYPE first, Node KEY_VALUE_GENERIC_TYPE forwardFence, Node KEY_VALUE_GENERIC_TYPE backwardFence, boolean isForward) { next = first; + previous = first == null ? null : movePrevious(first); this.forwardFence = forwardFence == null ? EMPTY_KEY_VALUE : forwardFence.key; this.backwardFence = backwardFence == null ? EMPTY_KEY_VALUE : backwardFence.key; unboundForwardFence = forwardFence == null; unboundBackwardFence = backwardFence == null; + this.isForward = isForward; + } + + protected Node KEY_VALUE_GENERIC_TYPE moveNext(Node KEY_VALUE_GENERIC_TYPE node) { + return node.next(); + } + + protected Node KEY_VALUE_GENERIC_TYPE movePrevious(Node KEY_VALUE_GENERIC_TYPE node) { + return node.previous(); } public boolean hasNext() { @@ -2187,26 +2228,30 @@ public class AVL_TREE_MAP KEY_VALUE_GENERIC_TYPE extends ABSTRACT_MAP KEY_VALUE_ protected Node KEY_VALUE_GENERIC_TYPE nextEntry() { lastReturned = next; + previous = next; Node KEY_VALUE_GENERIC_TYPE result = next; - next = next.next(); - wasForward = true; + next = moveNext(next); + wasForward = isForward; return result; } public boolean hasPrevious() { - return next != null && (unboundBackwardFence || next.key != backwardFence); + return previous != null && (unboundBackwardFence || previous.key != backwardFence); } protected Node KEY_VALUE_GENERIC_TYPE previousEntry() { - lastReturned = next; - Node KEY_VALUE_GENERIC_TYPE result = next; - next = next.previous(); - wasForward = false; + lastReturned = previous; + next = previous; + Node KEY_VALUE_GENERIC_TYPE result = previous; + previous = movePrevious(previous); + wasForward = !isForward; return result; } public void remove() { if(lastReturned == null) throw new IllegalStateException(); + if(next == lastReturned) next = moveNext(next); + if(previous == lastReturned) previous = movePrevious(previous); if(wasForward && lastReturned.needsSuccessor()) next = lastReturned; map.removeNode(lastReturned); lastReturned = null; @@ -2520,19 +2565,29 @@ public class AVL_TREE_MAP KEY_VALUE_GENERIC_TYPE extends ABSTRACT_MAP KEY_VALUE_ class DescendingKeyIterator extends MapEntryIterator implements BI_ITERATOR KEY_GENERIC_TYPE { public DescendingKeyIterator(Node KEY_VALUE_GENERIC_TYPE first) { - super(first); - } - - @Override - public KEY_TYPE PREVIOUS() { - if(!hasPrevious()) throw new NoSuchElementException(); - return nextEntry().key; + super(first, false); } + @Override + protected Node KEY_VALUE_GENERIC_TYPE moveNext(Node KEY_VALUE_GENERIC_TYPE node) { + return node.previous(); + } + + @Override + protected Node KEY_VALUE_GENERIC_TYPE movePrevious(Node KEY_VALUE_GENERIC_TYPE node) { + return node.next(); + } + + @Override + public KEY_TYPE PREVIOUS() { + if(!hasPrevious()) throw new NoSuchElementException(); + return previousEntry().key; + } + @Override public KEY_TYPE NEXT() { if(!hasNext()) throw new NoSuchElementException(); - return previousEntry().key; + return nextEntry().key; } } @@ -2540,7 +2595,7 @@ public class AVL_TREE_MAP KEY_VALUE_GENERIC_TYPE extends ABSTRACT_MAP KEY_VALUE_ { public AscendingMapEntryIterator(Node KEY_VALUE_GENERIC_TYPE first) { - super(first); + super(first, true); } @Override @@ -2559,7 +2614,7 @@ public class AVL_TREE_MAP KEY_VALUE_GENERIC_TYPE extends ABSTRACT_MAP KEY_VALUE_ class AscendingValueIterator extends MapEntryIterator implements VALUE_BI_ITERATOR VALUE_GENERIC_TYPE { public AscendingValueIterator(Node KEY_VALUE_GENERIC_TYPE first) { - super(first); + super(first, true); } @Override @@ -2578,7 +2633,7 @@ public class AVL_TREE_MAP KEY_VALUE_GENERIC_TYPE extends ABSTRACT_MAP KEY_VALUE_ class AscendingKeyIterator extends MapEntryIterator implements BI_ITERATOR KEY_GENERIC_TYPE { public AscendingKeyIterator(Node KEY_VALUE_GENERIC_TYPE first) { - super(first); + super(first, true); } @Override @@ -2596,13 +2651,24 @@ public class AVL_TREE_MAP KEY_VALUE_GENERIC_TYPE extends ABSTRACT_MAP KEY_VALUE_ abstract class MapEntryIterator { + final boolean isForward; boolean wasMoved = false; Node KEY_VALUE_GENERIC_TYPE lastReturned; Node KEY_VALUE_GENERIC_TYPE next; + Node KEY_VALUE_GENERIC_TYPE previous; - public MapEntryIterator(Node KEY_VALUE_GENERIC_TYPE first) - { + public MapEntryIterator(Node KEY_VALUE_GENERIC_TYPE first, boolean isForward) { next = first; + previous = first == null ? null : movePrevious(first); + this.isForward = isForward; + } + + protected Node KEY_VALUE_GENERIC_TYPE moveNext(Node KEY_VALUE_GENERIC_TYPE node) { + return node.next(); + } + + protected Node KEY_VALUE_GENERIC_TYPE movePrevious(Node KEY_VALUE_GENERIC_TYPE node) { + return node.previous(); } public boolean hasNext() { @@ -2611,26 +2677,30 @@ public class AVL_TREE_MAP KEY_VALUE_GENERIC_TYPE extends ABSTRACT_MAP KEY_VALUE_ protected Node KEY_VALUE_GENERIC_TYPE nextEntry() { lastReturned = next; + previous = next; Node KEY_VALUE_GENERIC_TYPE result = next; - next = next.next(); - wasMoved = true; + next = moveNext(next); + wasMoved = isForward; return result; } public boolean hasPrevious() { - return next != null; + return previous != null; } protected Node KEY_VALUE_GENERIC_TYPE previousEntry() { - lastReturned = next; - Node KEY_VALUE_GENERIC_TYPE result = next; - next = next.previous(); - wasMoved = false; + lastReturned = previous; + next = previous; + Node KEY_VALUE_GENERIC_TYPE result = previous; + previous = movePrevious(previous); + wasMoved = !isForward; return result; } public void remove() { if(lastReturned == null) throw new IllegalStateException(); + if(next == lastReturned) next = moveNext(next); + if(previous == lastReturned) previous = movePrevious(previous); if(wasMoved && lastReturned.needsSuccessor()) next = lastReturned; removeNode(lastReturned); lastReturned = null; diff --git a/src/builder/resources/speiger/assets/collections/templates/maps/impl/tree/RBTreeMap.template b/src/builder/resources/speiger/assets/collections/templates/maps/impl/tree/RBTreeMap.template index bac1b9f6..bcdc169a 100644 --- a/src/builder/resources/speiger/assets/collections/templates/maps/impl/tree/RBTreeMap.template +++ b/src/builder/resources/speiger/assets/collections/templates/maps/impl/tree/RBTreeMap.template @@ -2118,26 +2118,36 @@ public class RB_TREE_MAP KEY_VALUE_GENERIC_TYPE extends ABSTRACT_MAP KEY_VALUE_G class DecsendingSubEntryIterator extends SubMapEntryIterator implements ObjectBidirectionalIterator { public DecsendingSubEntryIterator(Node KEY_VALUE_GENERIC_TYPE first, Node KEY_VALUE_GENERIC_TYPE forwardFence, Node KEY_VALUE_GENERIC_TYPE backwardFence) { - super(first, forwardFence, backwardFence); + super(first, forwardFence, backwardFence, false); + } + + @Override + protected Node KEY_VALUE_GENERIC_TYPE moveNext(Node KEY_VALUE_GENERIC_TYPE node) { + return node.previous(); + } + + @Override + protected Node KEY_VALUE_GENERIC_TYPE movePrevious(Node KEY_VALUE_GENERIC_TYPE node) { + return node.next(); } @Override public MAP.Entry KEY_VALUE_GENERIC_TYPE previous() { if(!hasPrevious()) throw new NoSuchElementException(); - return nextEntry(); + return previousEntry(); } @Override public MAP.Entry KEY_VALUE_GENERIC_TYPE next() { if(!hasNext()) throw new NoSuchElementException(); - return previousEntry(); + return nextEntry(); } } class AcsendingSubEntryIterator extends SubMapEntryIterator implements ObjectBidirectionalIterator { public AcsendingSubEntryIterator(Node KEY_VALUE_GENERIC_TYPE first, Node KEY_VALUE_GENERIC_TYPE forwardFence, Node KEY_VALUE_GENERIC_TYPE backwardFence) { - super(first, forwardFence, backwardFence); + super(first, forwardFence, backwardFence, true); } @Override @@ -2156,26 +2166,36 @@ public class RB_TREE_MAP KEY_VALUE_GENERIC_TYPE extends ABSTRACT_MAP KEY_VALUE_G class DecsendingSubKeyIterator extends SubMapEntryIterator implements BI_ITERATOR KEY_GENERIC_TYPE { public DecsendingSubKeyIterator(Node KEY_VALUE_GENERIC_TYPE first, Node KEY_VALUE_GENERIC_TYPE forwardFence, Node KEY_VALUE_GENERIC_TYPE backwardFence) { - super(first, forwardFence, backwardFence); + super(first, forwardFence, backwardFence, false); + } + + @Override + protected Node KEY_VALUE_GENERIC_TYPE moveNext(Node KEY_VALUE_GENERIC_TYPE node) { + return node.previous(); + } + + @Override + protected Node KEY_VALUE_GENERIC_TYPE movePrevious(Node KEY_VALUE_GENERIC_TYPE node) { + return node.next(); } @Override public KEY_TYPE PREVIOUS() { if(!hasPrevious()) throw new NoSuchElementException(); - return nextEntry().key; + return previousEntry().key; } @Override public KEY_TYPE NEXT() { if(!hasNext()) throw new NoSuchElementException(); - return previousEntry().key; + return nextEntry().key; } } class AcsendingSubKeyIterator extends SubMapEntryIterator implements BI_ITERATOR KEY_GENERIC_TYPE { public AcsendingSubKeyIterator(Node KEY_VALUE_GENERIC_TYPE first, Node KEY_VALUE_GENERIC_TYPE forwardFence, Node KEY_VALUE_GENERIC_TYPE backwardFence) { - super(first, forwardFence, backwardFence); + super(first, forwardFence, backwardFence, true); } @Override @@ -2194,7 +2214,7 @@ public class RB_TREE_MAP KEY_VALUE_GENERIC_TYPE extends ABSTRACT_MAP KEY_VALUE_G class AcsendingSubValueIterator extends SubMapEntryIterator implements VALUE_BI_ITERATOR VALUE_GENERIC_TYPE { public AcsendingSubValueIterator(Node KEY_VALUE_GENERIC_TYPE first, Node KEY_VALUE_GENERIC_TYPE forwardFence, Node KEY_VALUE_GENERIC_TYPE backwardFence) { - super(first, forwardFence, backwardFence); + super(first, forwardFence, backwardFence, true); } @Override @@ -2213,39 +2233,60 @@ public class RB_TREE_MAP KEY_VALUE_GENERIC_TYPE extends ABSTRACT_MAP KEY_VALUE_G class DecsendingSubValueIterator extends SubMapEntryIterator implements VALUE_BI_ITERATOR VALUE_GENERIC_TYPE { public DecsendingSubValueIterator(Node KEY_VALUE_GENERIC_TYPE first, Node KEY_VALUE_GENERIC_TYPE forwardFence, Node KEY_VALUE_GENERIC_TYPE backwardFence) { - super(first, forwardFence, backwardFence); + super(first, forwardFence, backwardFence, false); + } + + @Override + protected Node KEY_VALUE_GENERIC_TYPE moveNext(Node KEY_VALUE_GENERIC_TYPE node) { + return node.previous(); + } + + @Override + protected Node KEY_VALUE_GENERIC_TYPE movePrevious(Node KEY_VALUE_GENERIC_TYPE node) { + return node.next(); } @Override public VALUE_TYPE VALUE_PREVIOUS() { if(!hasPrevious()) throw new NoSuchElementException(); - return nextEntry().value; + return previousEntry().value; } @Override public VALUE_TYPE VALUE_NEXT() { if(!hasNext()) throw new NoSuchElementException(); - return previousEntry().value; + return nextEntry().value; } } abstract class SubMapEntryIterator { + final boolean isForward; boolean wasForward; Node KEY_VALUE_GENERIC_TYPE lastReturned; Node KEY_VALUE_GENERIC_TYPE next; + Node KEY_VALUE_GENERIC_TYPE previous; boolean unboundForwardFence; boolean unboundBackwardFence; KEY_TYPE forwardFence; KEY_TYPE backwardFence; - public SubMapEntryIterator(Node KEY_VALUE_GENERIC_TYPE first, Node KEY_VALUE_GENERIC_TYPE forwardFence, Node KEY_VALUE_GENERIC_TYPE backwardFence) - { + public SubMapEntryIterator(Node KEY_VALUE_GENERIC_TYPE first, Node KEY_VALUE_GENERIC_TYPE forwardFence, Node KEY_VALUE_GENERIC_TYPE backwardFence, boolean isForward) { next = first; + previous = first == null ? null : movePrevious(first); this.forwardFence = forwardFence == null ? EMPTY_KEY_VALUE : forwardFence.key; this.backwardFence = backwardFence == null ? EMPTY_KEY_VALUE : backwardFence.key; unboundForwardFence = forwardFence == null; unboundBackwardFence = backwardFence == null; + this.isForward = isForward; + } + + protected Node KEY_VALUE_GENERIC_TYPE moveNext(Node KEY_VALUE_GENERIC_TYPE node) { + return node.next(); + } + + protected Node KEY_VALUE_GENERIC_TYPE movePrevious(Node KEY_VALUE_GENERIC_TYPE node) { + return node.previous(); } public boolean hasNext() { @@ -2254,26 +2295,30 @@ public class RB_TREE_MAP KEY_VALUE_GENERIC_TYPE extends ABSTRACT_MAP KEY_VALUE_G protected Node KEY_VALUE_GENERIC_TYPE nextEntry() { lastReturned = next; + previous = next; Node KEY_VALUE_GENERIC_TYPE result = next; - next = next.next(); - wasForward = true; + next = moveNext(next); + wasForward = isForward; return result; } public boolean hasPrevious() { - return next != null && (unboundBackwardFence || next.key != backwardFence); + return previous != null && (unboundBackwardFence || previous.key != backwardFence); } protected Node KEY_VALUE_GENERIC_TYPE previousEntry() { - lastReturned = next; - Node KEY_VALUE_GENERIC_TYPE result = next; - next = next.previous(); - wasForward = false; + lastReturned = previous; + next = previous; + Node KEY_VALUE_GENERIC_TYPE result = previous; + previous = movePrevious(previous); + wasForward = !isForward; return result; } public void remove() { if(lastReturned == null) throw new IllegalStateException(); + if(next == lastReturned) next = moveNext(next); + if(previous == lastReturned) previous = movePrevious(previous); if(wasForward && lastReturned.needsSuccessor()) next = lastReturned; map.removeNode(lastReturned); lastReturned = null; @@ -2587,19 +2632,29 @@ public class RB_TREE_MAP KEY_VALUE_GENERIC_TYPE extends ABSTRACT_MAP KEY_VALUE_G class DescendingKeyIterator extends MapEntryIterator implements BI_ITERATOR KEY_GENERIC_TYPE { public DescendingKeyIterator(Node KEY_VALUE_GENERIC_TYPE first) { - super(first); - } - - @Override - public KEY_TYPE PREVIOUS() { - if(!hasPrevious()) throw new NoSuchElementException(); - return nextEntry().key; + super(first, false); } + @Override + protected Node KEY_VALUE_GENERIC_TYPE moveNext(Node KEY_VALUE_GENERIC_TYPE node) { + return node.previous(); + } + + @Override + protected Node KEY_VALUE_GENERIC_TYPE movePrevious(Node KEY_VALUE_GENERIC_TYPE node) { + return node.next(); + } + + @Override + public KEY_TYPE PREVIOUS() { + if(!hasPrevious()) throw new NoSuchElementException(); + return previousEntry().key; + } + @Override public KEY_TYPE NEXT() { if(!hasNext()) throw new NoSuchElementException(); - return previousEntry().key; + return nextEntry().key; } } @@ -2607,7 +2662,7 @@ public class RB_TREE_MAP KEY_VALUE_GENERIC_TYPE extends ABSTRACT_MAP KEY_VALUE_G { public AscendingMapEntryIterator(Node KEY_VALUE_GENERIC_TYPE first) { - super(first); + super(first, true); } @Override @@ -2626,7 +2681,7 @@ public class RB_TREE_MAP KEY_VALUE_GENERIC_TYPE extends ABSTRACT_MAP KEY_VALUE_G class AscendingValueIterator extends MapEntryIterator implements VALUE_BI_ITERATOR VALUE_GENERIC_TYPE { public AscendingValueIterator(Node KEY_VALUE_GENERIC_TYPE first) { - super(first); + super(first, true); } @Override @@ -2645,7 +2700,7 @@ public class RB_TREE_MAP KEY_VALUE_GENERIC_TYPE extends ABSTRACT_MAP KEY_VALUE_G class AscendingKeyIterator extends MapEntryIterator implements BI_ITERATOR KEY_GENERIC_TYPE { public AscendingKeyIterator(Node KEY_VALUE_GENERIC_TYPE first) { - super(first); + super(first, true); } @Override @@ -2663,13 +2718,24 @@ public class RB_TREE_MAP KEY_VALUE_GENERIC_TYPE extends ABSTRACT_MAP KEY_VALUE_G abstract class MapEntryIterator { + final boolean isForward; boolean wasMoved = false; Node KEY_VALUE_GENERIC_TYPE lastReturned; Node KEY_VALUE_GENERIC_TYPE next; + Node KEY_VALUE_GENERIC_TYPE previous; - public MapEntryIterator(Node KEY_VALUE_GENERIC_TYPE first) - { + public MapEntryIterator(Node KEY_VALUE_GENERIC_TYPE first, boolean isForward) { next = first; + previous = first == null ? null : movePrevious(first); + this.isForward = isForward; + } + + protected Node KEY_VALUE_GENERIC_TYPE moveNext(Node KEY_VALUE_GENERIC_TYPE node) { + return node.next(); + } + + protected Node KEY_VALUE_GENERIC_TYPE movePrevious(Node KEY_VALUE_GENERIC_TYPE node) { + return node.previous(); } public boolean hasNext() { @@ -2678,26 +2744,30 @@ public class RB_TREE_MAP KEY_VALUE_GENERIC_TYPE extends ABSTRACT_MAP KEY_VALUE_G protected Node KEY_VALUE_GENERIC_TYPE nextEntry() { lastReturned = next; + previous = next; Node KEY_VALUE_GENERIC_TYPE result = next; - next = next.next(); - wasMoved = true; + next = moveNext(next); + wasMoved = isForward; return result; } public boolean hasPrevious() { - return next != null; + return previous != null; } protected Node KEY_VALUE_GENERIC_TYPE previousEntry() { - lastReturned = next; - Node KEY_VALUE_GENERIC_TYPE result = next; - next = next.previous(); - wasMoved = false; + lastReturned = previous; + next = previous; + Node KEY_VALUE_GENERIC_TYPE result = previous; + previous = movePrevious(previous); + wasMoved = !isForward; return result; } public void remove() { if(lastReturned == null) throw new IllegalStateException(); + if(next == lastReturned) next = moveNext(next); + if(previous == lastReturned) previous = movePrevious(previous); if(wasMoved && lastReturned.needsSuccessor()) next = lastReturned; removeNode(lastReturned); lastReturned = null; diff --git a/src/builder/resources/speiger/assets/collections/templates/maps/interfaces/OrderedMap.template b/src/builder/resources/speiger/assets/collections/templates/maps/interfaces/OrderedMap.template index e3a19644..8ebd4dd6 100644 --- a/src/builder/resources/speiger/assets/collections/templates/maps/interfaces/OrderedMap.template +++ b/src/builder/resources/speiger/assets/collections/templates/maps/interfaces/OrderedMap.template @@ -1,6 +1,9 @@ package speiger.src.collections.PACKAGE.maps.interfaces; import speiger.src.collections.PACKAGE.utils.maps.MAPS; +#if !TYPE_OBJECT +import speiger.src.collections.PACKAGE.sets.ORDERED_SET; +#endif import speiger.src.collections.objects.collections.ObjectBidirectionalIterator; import speiger.src.collections.objects.sets.ObjectOrderedSet; /** @@ -94,6 +97,10 @@ public interface ORDERED_MAP KEY_VALUE_GENERIC_TYPE extends MAP KEY_VALUE_GENERI @Override public ORDERED_MAP KEY_VALUE_GENERIC_TYPE copy(); + @Override + public ORDERED_SET KEY_GENERIC_TYPE keySet(); + @Override + public ObjectOrderedSet ENTRY_SET(); /** * Creates a Wrapped SortedMap that is Synchronized diff --git a/src/builder/resources/speiger/assets/collections/templates/sets/AVLTreeSet.template b/src/builder/resources/speiger/assets/collections/templates/sets/AVLTreeSet.template index 4b707f1f..d3614a5d 100644 --- a/src/builder/resources/speiger/assets/collections/templates/sets/AVLTreeSet.template +++ b/src/builder/resources/speiger/assets/collections/templates/sets/AVLTreeSet.template @@ -1298,6 +1298,7 @@ public class AVL_TREE_SET KEY_GENERIC_TYPE extends ABSTRACT_SET KEY_GENERIC_TYPE { Entry KEY_GENERIC_TYPE lastReturned; Entry KEY_GENERIC_TYPE next; + Entry KEY_GENERIC_TYPE previous; boolean forwards = false; boolean unboundForwardFence; boolean unboundBackwardFence; @@ -1307,6 +1308,7 @@ public class AVL_TREE_SET KEY_GENERIC_TYPE extends ABSTRACT_SET KEY_GENERIC_TYPE public AscendingSubSetIterator(Entry KEY_GENERIC_TYPE first, Entry KEY_GENERIC_TYPE forwardFence, Entry KEY_GENERIC_TYPE backwardFence) { next = first; + previous = first == null ? null : first.previous(); this.forwardFence = forwardFence == null ? EMPTY_KEY_VALUE : forwardFence.key; this.backwardFence = backwardFence == null ? EMPTY_KEY_VALUE : backwardFence.key; unboundForwardFence = forwardFence == null; @@ -1322,6 +1324,7 @@ public class AVL_TREE_SET KEY_GENERIC_TYPE extends ABSTRACT_SET KEY_GENERIC_TYPE public KEY_TYPE NEXT() { if(!hasNext()) throw new NoSuchElementException(); lastReturned = next; + previous = next; KEY_TYPE result = next.key; next = next.next(); forwards = true; @@ -1330,15 +1333,16 @@ public class AVL_TREE_SET KEY_GENERIC_TYPE extends ABSTRACT_SET KEY_GENERIC_TYPE @Override public boolean hasPrevious() { - return next != null && (unboundBackwardFence || next.key != backwardFence); + return previous != null && (unboundBackwardFence || previous.key != backwardFence); } @Override public KEY_TYPE PREVIOUS() { if(!hasPrevious()) throw new NoSuchElementException(); - lastReturned = next; - KEY_TYPE result = next.key; - next = next.previous(); + lastReturned = previous; + next = previous; + KEY_TYPE result = previous.key; + previous = previous.previous(); forwards = false; return result; } @@ -1346,6 +1350,8 @@ public class AVL_TREE_SET KEY_GENERIC_TYPE extends ABSTRACT_SET KEY_GENERIC_TYPE @Override public void remove() { if(lastReturned == null) throw new IllegalStateException(); + if(previous == lastReturned) previous = previous.previous(); + if(next == lastReturned) next = next.next(); if(forwards && lastReturned.needsSuccessor()) next = lastReturned; set.removeNode(lastReturned); lastReturned = null; @@ -1356,6 +1362,7 @@ public class AVL_TREE_SET KEY_GENERIC_TYPE extends ABSTRACT_SET KEY_GENERIC_TYPE { Entry KEY_GENERIC_TYPE lastReturned; Entry KEY_GENERIC_TYPE next; + Entry KEY_GENERIC_TYPE previous; boolean forwards = false; boolean unboundForwardFence; boolean unboundBackwardFence; @@ -1365,6 +1372,7 @@ public class AVL_TREE_SET KEY_GENERIC_TYPE extends ABSTRACT_SET KEY_GENERIC_TYPE public DescendingSubSetIterator(Entry KEY_GENERIC_TYPE first, Entry KEY_GENERIC_TYPE forwardFence, Entry KEY_GENERIC_TYPE backwardFence) { next = first; + previous = first == null ? null : first.next(); this.forwardFence = forwardFence == null ? EMPTY_KEY_VALUE : forwardFence.key; this.backwardFence = backwardFence == null ? EMPTY_KEY_VALUE : backwardFence.key; unboundForwardFence = forwardFence == null; @@ -1380,6 +1388,7 @@ public class AVL_TREE_SET KEY_GENERIC_TYPE extends ABSTRACT_SET KEY_GENERIC_TYPE public KEY_TYPE NEXT() { if(!hasNext()) throw new NoSuchElementException(); lastReturned = next; + previous = next; KEY_TYPE result = next.key; next = next.previous(); forwards = false; @@ -1388,15 +1397,16 @@ public class AVL_TREE_SET KEY_GENERIC_TYPE extends ABSTRACT_SET KEY_GENERIC_TYPE @Override public boolean hasPrevious() { - return next != null && (unboundBackwardFence || next.key != backwardFence); + return previous != null && (unboundBackwardFence || previous.key != backwardFence); } @Override public KEY_TYPE PREVIOUS() { if(!hasPrevious()) throw new NoSuchElementException(); - lastReturned = next; - KEY_TYPE result = next.key; - next = next.next(); + lastReturned = previous; + next = previous; + KEY_TYPE result = previous.key; + previous = previous.next(); forwards = true; return result; } @@ -1404,6 +1414,8 @@ public class AVL_TREE_SET KEY_GENERIC_TYPE extends ABSTRACT_SET KEY_GENERIC_TYPE @Override public void remove() { if(lastReturned == null) throw new IllegalStateException(); + if(previous == lastReturned) previous = previous.next(); + if(next == lastReturned) next = next.previous(); if(forwards && lastReturned.needsSuccessor()) next = lastReturned; set.removeNode(lastReturned); lastReturned = null; @@ -1415,11 +1427,13 @@ public class AVL_TREE_SET KEY_GENERIC_TYPE extends ABSTRACT_SET KEY_GENERIC_TYPE { Entry KEY_GENERIC_TYPE lastReturned; Entry KEY_GENERIC_TYPE next; + Entry KEY_GENERIC_TYPE previous; boolean forwards = false; public AscendingSetIterator(Entry KEY_GENERIC_TYPE first) { next = first; + previous = first == null ? null : first.previous(); } @Override @@ -1431,6 +1445,7 @@ public class AVL_TREE_SET KEY_GENERIC_TYPE extends ABSTRACT_SET KEY_GENERIC_TYPE public KEY_TYPE NEXT() { if(!hasNext()) throw new NoSuchElementException(); lastReturned = next; + previous = next; KEY_TYPE result = next.key; next = next.next(); forwards = true; @@ -1439,15 +1454,16 @@ public class AVL_TREE_SET KEY_GENERIC_TYPE extends ABSTRACT_SET KEY_GENERIC_TYPE @Override public boolean hasPrevious() { - return next != null; + return previous != null; } @Override public KEY_TYPE PREVIOUS() { if(!hasPrevious()) throw new NoSuchElementException(); - lastReturned = next; - KEY_TYPE result = next.key; - next = next.previous(); + lastReturned = previous; + next = previous; + KEY_TYPE result = previous.key; + previous = previous.previous(); forwards = false; return result; } @@ -1455,6 +1471,8 @@ public class AVL_TREE_SET KEY_GENERIC_TYPE extends ABSTRACT_SET KEY_GENERIC_TYPE @Override public void remove() { if(lastReturned == null) throw new IllegalStateException(); + if(lastReturned == previous) previous = previous.previous(); + if(lastReturned == next) next = next.next(); if(forwards && lastReturned.needsSuccessor()) next = lastReturned; removeNode(lastReturned); lastReturned = null; @@ -1465,11 +1483,13 @@ public class AVL_TREE_SET KEY_GENERIC_TYPE extends ABSTRACT_SET KEY_GENERIC_TYPE { Entry KEY_GENERIC_TYPE lastReturned; Entry KEY_GENERIC_TYPE next; + Entry KEY_GENERIC_TYPE previous; boolean forwards = false; public DescendingSetIterator(Entry KEY_GENERIC_TYPE first) { next = first; + previous = first == null ? null : first.next(); } @Override @@ -1481,6 +1501,7 @@ public class AVL_TREE_SET KEY_GENERIC_TYPE extends ABSTRACT_SET KEY_GENERIC_TYPE public KEY_TYPE NEXT() { if(!hasNext()) throw new NoSuchElementException(); lastReturned = next; + previous = next; KEY_TYPE result = next.key; next = next.previous(); forwards = false; @@ -1489,15 +1510,16 @@ public class AVL_TREE_SET KEY_GENERIC_TYPE extends ABSTRACT_SET KEY_GENERIC_TYPE @Override public boolean hasPrevious() { - return next != null; + return previous != null; } @Override public KEY_TYPE PREVIOUS() { if(!hasPrevious()) throw new NoSuchElementException(); - lastReturned = next; - KEY_TYPE result = next.key; - next = next.next(); + lastReturned = previous; + next = previous; + KEY_TYPE result = previous.key; + previous = previous.next(); forwards = true; return result; } @@ -1505,6 +1527,8 @@ public class AVL_TREE_SET KEY_GENERIC_TYPE extends ABSTRACT_SET KEY_GENERIC_TYPE @Override public void remove() { if(lastReturned == null) throw new IllegalStateException(); + if(lastReturned == previous) previous = previous.next(); + if(lastReturned == next) next = next.previous(); if(forwards && lastReturned.needsSuccessor()) next = lastReturned; removeNode(lastReturned); lastReturned = null; diff --git a/src/builder/resources/speiger/assets/collections/templates/sets/ArraySet.template b/src/builder/resources/speiger/assets/collections/templates/sets/ArraySet.template index d3d85707..f233f1a9 100644 --- a/src/builder/resources/speiger/assets/collections/templates/sets/ArraySet.template +++ b/src/builder/resources/speiger/assets/collections/templates/sets/ArraySet.template @@ -924,8 +924,8 @@ public class ARRAY_SET KEY_GENERIC_TYPE extends ABSTRACT_SET KEY_GENERIC_TYPE im @Override public KEY_TYPE PREVIOUS() { if(!hasPrevious()) throw new NoSuchElementException(); - lastReturned = index; - return data[index--]; + --index; + return data[(lastReturned = index)]; } @Override @@ -964,8 +964,9 @@ public class ARRAY_SET KEY_GENERIC_TYPE extends ABSTRACT_SET KEY_GENERIC_TYPE im @Override public int skip(int amount) { if(amount < 0) throw new IllegalStateException("Negative Numbers are not allowed"); - int steps = Math.min(amount, (size() - 1) - index); + int steps = Math.min(amount, size() - index); index += steps; + if(steps > 0) lastReturned = Math.min(index-1, size()-1); return steps; } @@ -974,6 +975,7 @@ public class ARRAY_SET KEY_GENERIC_TYPE extends ABSTRACT_SET KEY_GENERIC_TYPE im if(amount < 0) throw new IllegalStateException("Negative Numbers are not allowed"); int steps = Math.min(amount, index); index -= steps; + if(steps > 0) lastReturned = Math.min(index, size()-1); return steps; } } diff --git a/src/builder/resources/speiger/assets/collections/templates/sets/ImmutableOpenHashSet.template b/src/builder/resources/speiger/assets/collections/templates/sets/ImmutableOpenHashSet.template index c89657eb..90ebecf2 100644 --- a/src/builder/resources/speiger/assets/collections/templates/sets/ImmutableOpenHashSet.template +++ b/src/builder/resources/speiger/assets/collections/templates/sets/ImmutableOpenHashSet.template @@ -502,6 +502,28 @@ public class IMMUTABLE_HASH_SET KEY_GENERIC_TYPE extends ABSTRACT_SET KEY_GENERI } } + @Override + public int skip(int amount) { + int result = 0; + while(next != -1 && result != amount) { + current = previous = next; + next = (int)(links[current]); + result++; + } + return result; + } + + @Override + public int back(int amount) { + int result = 0; + while(previous != -1 && result != amount) { + current = next = previous; + previous = (int)(links[current] >> 32); + result++; + } + return result; + } + @Override public boolean hasNext() { return next != -1; @@ -530,9 +552,8 @@ public class IMMUTABLE_HASH_SET KEY_GENERIC_TYPE extends ABSTRACT_SET KEY_GENERI @Override public KEY_TYPE PREVIOUS() { if(!hasPrevious()) throw new NoSuchElementException(); - current = previous; + current = next = previous; previous = (int)(links[current] >> 32); - next = current; if(index >= 0) index--; return keys[current]; } @@ -540,9 +561,8 @@ public class IMMUTABLE_HASH_SET KEY_GENERIC_TYPE extends ABSTRACT_SET KEY_GENERI @Override public KEY_TYPE NEXT() { if(!hasNext()) throw new NoSuchElementException(); - current = next; + current = previous = next; next = (int)(links[current]); - previous = current; if(index >= 0) index++; return keys[current]; } diff --git a/src/builder/resources/speiger/assets/collections/templates/sets/LinkedOpenCustomHashSet.template b/src/builder/resources/speiger/assets/collections/templates/sets/LinkedOpenCustomHashSet.template index 3780fe88..8b91d54a 100644 --- a/src/builder/resources/speiger/assets/collections/templates/sets/LinkedOpenCustomHashSet.template +++ b/src/builder/resources/speiger/assets/collections/templates/sets/LinkedOpenCustomHashSet.template @@ -717,6 +717,28 @@ public class LINKED_CUSTOM_HASH_SET KEY_GENERIC_TYPE extends CUSTOM_HASH_SET KEY return previous != -1; } + @Override + public int skip(int amount) { + int result = 0; + while(next != -1 && result != amount) { + current = previous = next; + next = (int)(links[current]); + result++; + } + return result; + } + + @Override + public int back(int amount) { + int result = 0; + while(previous != -1 && result != amount) { + current = next = previous; + previous = (int)(links[current] >> 32); + result++; + } + return result; + } + @Override public int nextIndex() { ensureIndexKnown(); @@ -775,9 +797,8 @@ public class LINKED_CUSTOM_HASH_SET KEY_GENERIC_TYPE extends CUSTOM_HASH_SET KEY @Override public KEY_TYPE PREVIOUS() { if(!hasPrevious()) throw new NoSuchElementException(); - current = previous; + current = next = previous; previous = (int)(links[current] >> 32); - next = current; if(index >= 0) index--; return keys[current]; } @@ -785,9 +806,8 @@ public class LINKED_CUSTOM_HASH_SET KEY_GENERIC_TYPE extends CUSTOM_HASH_SET KEY @Override public KEY_TYPE NEXT() { if(!hasNext()) throw new NoSuchElementException(); - current = next; + current = previous = next; next = (int)(links[current]); - previous = current; if(index >= 0) index++; return keys[current]; } diff --git a/src/builder/resources/speiger/assets/collections/templates/sets/LinkedOpenHashSet.template b/src/builder/resources/speiger/assets/collections/templates/sets/LinkedOpenHashSet.template index 9b08a6f3..305b90d7 100644 --- a/src/builder/resources/speiger/assets/collections/templates/sets/LinkedOpenHashSet.template +++ b/src/builder/resources/speiger/assets/collections/templates/sets/LinkedOpenHashSet.template @@ -678,6 +678,28 @@ public class LINKED_HASH_SET KEY_GENERIC_TYPE extends HASH_SET KEY_GENERIC_TYPE } } + @Override + public int skip(int amount) { + int result = 0; + while(next != -1 && result != amount) { + current = previous = next; + next = (int)(links[current]); + result++; + } + return result; + } + + @Override + public int back(int amount) { + int result = 0; + while(previous != -1 && result != amount) { + current = next = previous; + previous = (int)(links[current] >> 32); + result++; + } + return result; + } + @Override public boolean hasNext() { return next != -1; @@ -746,9 +768,8 @@ public class LINKED_HASH_SET KEY_GENERIC_TYPE extends HASH_SET KEY_GENERIC_TYPE @Override public KEY_TYPE PREVIOUS() { if(!hasPrevious()) throw new NoSuchElementException(); - current = previous; + current = next = previous; previous = (int)(links[current] >> 32); - next = current; if(index >= 0) index--; return keys[current]; } @@ -756,9 +777,8 @@ public class LINKED_HASH_SET KEY_GENERIC_TYPE extends HASH_SET KEY_GENERIC_TYPE @Override public KEY_TYPE NEXT() { if(!hasNext()) throw new NoSuchElementException(); - current = next; + current = previous = next; next = (int)(links[current]); - previous = current; if(index >= 0) index++; return keys[current]; } diff --git a/src/builder/resources/speiger/assets/collections/templates/sets/RBTreeSet.template b/src/builder/resources/speiger/assets/collections/templates/sets/RBTreeSet.template index 125a7931..5841a052 100644 --- a/src/builder/resources/speiger/assets/collections/templates/sets/RBTreeSet.template +++ b/src/builder/resources/speiger/assets/collections/templates/sets/RBTreeSet.template @@ -1359,6 +1359,7 @@ public class RB_TREE_SET KEY_GENERIC_TYPE extends ABSTRACT_SET KEY_GENERIC_TYPE { Entry KEY_GENERIC_TYPE lastReturned; Entry KEY_GENERIC_TYPE next; + Entry KEY_GENERIC_TYPE previous; boolean forwards = false; boolean unboundForwardFence; boolean unboundBackwardFence; @@ -1368,6 +1369,7 @@ public class RB_TREE_SET KEY_GENERIC_TYPE extends ABSTRACT_SET KEY_GENERIC_TYPE public AscendingSubSetIterator(Entry KEY_GENERIC_TYPE first, Entry KEY_GENERIC_TYPE forwardFence, Entry KEY_GENERIC_TYPE backwardFence) { next = first; + previous = first == null ? null : first.previous(); this.forwardFence = forwardFence == null ? EMPTY_KEY_VALUE : forwardFence.key; this.backwardFence = backwardFence == null ? EMPTY_KEY_VALUE : backwardFence.key; unboundForwardFence = forwardFence == null; @@ -1383,6 +1385,7 @@ public class RB_TREE_SET KEY_GENERIC_TYPE extends ABSTRACT_SET KEY_GENERIC_TYPE public KEY_TYPE NEXT() { if(!hasNext()) throw new NoSuchElementException(); lastReturned = next; + previous = next; KEY_TYPE result = next.key; next = next.next(); forwards = true; @@ -1391,15 +1394,16 @@ public class RB_TREE_SET KEY_GENERIC_TYPE extends ABSTRACT_SET KEY_GENERIC_TYPE @Override public boolean hasPrevious() { - return next != null && (unboundBackwardFence || next.key != backwardFence); + return previous != null && (unboundBackwardFence || previous.key != backwardFence); } @Override public KEY_TYPE PREVIOUS() { if(!hasPrevious()) throw new NoSuchElementException(); - lastReturned = next; - KEY_TYPE result = next.key; - next = next.previous(); + lastReturned = previous; + next = previous; + KEY_TYPE result = previous.key; + previous = previous.previous(); forwards = false; return result; } @@ -1407,6 +1411,8 @@ public class RB_TREE_SET KEY_GENERIC_TYPE extends ABSTRACT_SET KEY_GENERIC_TYPE @Override public void remove() { if(lastReturned == null) throw new IllegalStateException(); + if(previous == lastReturned) previous = previous.previous(); + if(next == lastReturned) next = next.next(); if(forwards && lastReturned.needsSuccessor()) next = lastReturned; set.removeNode(lastReturned); lastReturned = null; @@ -1417,6 +1423,7 @@ public class RB_TREE_SET KEY_GENERIC_TYPE extends ABSTRACT_SET KEY_GENERIC_TYPE { Entry KEY_GENERIC_TYPE lastReturned; Entry KEY_GENERIC_TYPE next; + Entry KEY_GENERIC_TYPE previous; boolean forwards = false; boolean unboundForwardFence; boolean unboundBackwardFence; @@ -1426,6 +1433,7 @@ public class RB_TREE_SET KEY_GENERIC_TYPE extends ABSTRACT_SET KEY_GENERIC_TYPE public DescendingSubSetIterator(Entry KEY_GENERIC_TYPE first, Entry KEY_GENERIC_TYPE forwardFence, Entry KEY_GENERIC_TYPE backwardFence) { next = first; + previous = first == null ? null : first.next(); this.forwardFence = forwardFence == null ? EMPTY_KEY_VALUE : forwardFence.key; this.backwardFence = backwardFence == null ? EMPTY_KEY_VALUE : backwardFence.key; unboundForwardFence = forwardFence == null; @@ -1441,6 +1449,7 @@ public class RB_TREE_SET KEY_GENERIC_TYPE extends ABSTRACT_SET KEY_GENERIC_TYPE public KEY_TYPE NEXT() { if(!hasNext()) throw new NoSuchElementException(); lastReturned = next; + previous = next; KEY_TYPE result = next.key; next = next.previous(); forwards = false; @@ -1449,15 +1458,16 @@ public class RB_TREE_SET KEY_GENERIC_TYPE extends ABSTRACT_SET KEY_GENERIC_TYPE @Override public boolean hasPrevious() { - return next != null && (unboundBackwardFence || next.key != backwardFence); + return previous != null && (unboundBackwardFence || previous.key != backwardFence); } @Override public KEY_TYPE PREVIOUS() { if(!hasPrevious()) throw new NoSuchElementException(); - lastReturned = next; - KEY_TYPE result = next.key; - next = next.next(); + lastReturned = previous; + next = previous; + KEY_TYPE result = previous.key; + previous = previous.next(); forwards = true; return result; } @@ -1465,6 +1475,8 @@ public class RB_TREE_SET KEY_GENERIC_TYPE extends ABSTRACT_SET KEY_GENERIC_TYPE @Override public void remove() { if(lastReturned == null) throw new IllegalStateException(); + if(previous == lastReturned) previous = previous.next(); + if(next == lastReturned) next = next.previous(); if(forwards && lastReturned.needsSuccessor()) next = lastReturned; set.removeNode(lastReturned); lastReturned = null; @@ -1476,11 +1488,13 @@ public class RB_TREE_SET KEY_GENERIC_TYPE extends ABSTRACT_SET KEY_GENERIC_TYPE { Entry KEY_GENERIC_TYPE lastReturned; Entry KEY_GENERIC_TYPE next; + Entry KEY_GENERIC_TYPE previous; boolean forwards = false; public AscendingSetIterator(Entry KEY_GENERIC_TYPE first) { next = first; + previous = first == null ? null : first.previous(); } @Override @@ -1492,6 +1506,7 @@ public class RB_TREE_SET KEY_GENERIC_TYPE extends ABSTRACT_SET KEY_GENERIC_TYPE public KEY_TYPE NEXT() { if(!hasNext()) throw new NoSuchElementException(); lastReturned = next; + previous = next; KEY_TYPE result = next.key; next = next.next(); forwards = true; @@ -1500,15 +1515,16 @@ public class RB_TREE_SET KEY_GENERIC_TYPE extends ABSTRACT_SET KEY_GENERIC_TYPE @Override public boolean hasPrevious() { - return next != null; + return previous != null; } @Override public KEY_TYPE PREVIOUS() { if(!hasPrevious()) throw new NoSuchElementException(); - lastReturned = next; - KEY_TYPE result = next.key; - next = next.previous(); + lastReturned = previous; + next = previous; + KEY_TYPE result = previous.key; + previous = previous.previous(); forwards = false; return result; } @@ -1516,6 +1532,8 @@ public class RB_TREE_SET KEY_GENERIC_TYPE extends ABSTRACT_SET KEY_GENERIC_TYPE @Override public void remove() { if(lastReturned == null) throw new IllegalStateException(); + if(lastReturned == previous) previous = previous.previous(); + if(lastReturned == next) next = next.next(); if(forwards && lastReturned.needsSuccessor()) next = lastReturned; removeNode(lastReturned); lastReturned = null; @@ -1526,11 +1544,13 @@ public class RB_TREE_SET KEY_GENERIC_TYPE extends ABSTRACT_SET KEY_GENERIC_TYPE { Entry KEY_GENERIC_TYPE lastReturned; Entry KEY_GENERIC_TYPE next; + Entry KEY_GENERIC_TYPE previous; boolean forwards = false; public DescendingSetIterator(Entry KEY_GENERIC_TYPE first) { next = first; + previous = first == null ? null : first.next(); } @Override @@ -1542,6 +1562,7 @@ public class RB_TREE_SET KEY_GENERIC_TYPE extends ABSTRACT_SET KEY_GENERIC_TYPE public KEY_TYPE NEXT() { if(!hasNext()) throw new NoSuchElementException(); lastReturned = next; + previous = next; KEY_TYPE result = next.key; next = next.previous(); forwards = false; @@ -1550,15 +1571,16 @@ public class RB_TREE_SET KEY_GENERIC_TYPE extends ABSTRACT_SET KEY_GENERIC_TYPE @Override public boolean hasPrevious() { - return next != null; + return previous != null; } @Override public KEY_TYPE PREVIOUS() { if(!hasPrevious()) throw new NoSuchElementException(); - lastReturned = next; - KEY_TYPE result = next.key; - next = next.next(); + lastReturned = previous; + next = previous; + KEY_TYPE result = previous.key; + previous = previous.next(); forwards = true; return result; } @@ -1566,6 +1588,8 @@ public class RB_TREE_SET KEY_GENERIC_TYPE extends ABSTRACT_SET KEY_GENERIC_TYPE @Override public void remove() { if(lastReturned == null) throw new IllegalStateException(); + if(lastReturned == previous) previous = previous.next(); + if(lastReturned == next) next = next.previous(); if(forwards && lastReturned.needsSuccessor()) next = lastReturned; removeNode(lastReturned); lastReturned = null; diff --git a/src/builder/resources/speiger/assets/collections/templates/utils/maps/Maps.template b/src/builder/resources/speiger/assets/collections/templates/utils/maps/Maps.template index 73e1078e..efa8f5a5 100644 --- a/src/builder/resources/speiger/assets/collections/templates/utils/maps/Maps.template +++ b/src/builder/resources/speiger/assets/collections/templates/utils/maps/Maps.template @@ -19,8 +19,11 @@ import speiger.src.collections.objects.collections.ObjectIterable; import speiger.src.collections.objects.collections.ObjectIterator; import speiger.src.collections.objects.sets.ObjectSet; #if !TYPE_BOOLEAN +import speiger.src.collections.objects.collections.ObjectBidirectionalIterator; +import speiger.src.collections.objects.utils.ObjectIterators; import speiger.src.collections.objects.utils.ObjectSets; #if !TYPE_OBJECT +import speiger.src.collections.objects.sets.ObjectOrderedSet; import speiger.src.collections.PACKAGE.functions.COMPARATOR; #endif import speiger.src.collections.PACKAGE.functions.consumer.BI_CONSUMER; @@ -35,6 +38,7 @@ import speiger.src.collections.PACKAGE.maps.interfaces.SORTED_MAP; import speiger.src.collections.PACKAGE.maps.interfaces.ORDERED_MAP; import speiger.src.collections.PACKAGE.sets.NAVIGABLE_SET; import speiger.src.collections.PACKAGE.sets.SORTED_SET; +import speiger.src.collections.PACKAGE.sets.ORDERED_SET; #if !TYPE_OBJECT import speiger.src.collections.PACKAGE.sets.SET; import speiger.src.collections.PACKAGE.utils.SETS; @@ -520,17 +524,28 @@ public class MAPS @Override public KEY_TYPE FIRST_ENTRY_KEY() { return map.FIRST_ENTRY_KEY(); } @Override - public KEY_TYPE POLL_FIRST_ENTRY_KEY() { return map.POLL_FIRST_ENTRY_KEY(); } + public KEY_TYPE POLL_FIRST_ENTRY_KEY() { throw new UnsupportedOperationException(); } @Override public KEY_TYPE LAST_ENTRY_KEY() { return map.LAST_ENTRY_KEY(); } @Override - public KEY_TYPE POLL_LAST_ENTRY_KEY() { return map.POLL_LAST_ENTRY_KEY(); } + public KEY_TYPE POLL_LAST_ENTRY_KEY() { throw new UnsupportedOperationException(); } @Override public VALUE_TYPE FIRST_ENTRY_VALUE() { return map.FIRST_ENTRY_VALUE(); } @Override public VALUE_TYPE LAST_ENTRY_VALUE() { return map.LAST_ENTRY_VALUE(); } @Override public ORDERED_MAP KEY_VALUE_GENERIC_TYPE copy() { return map.copy(); } + @Override + public ORDERED_SET KEY_GENERIC_TYPE keySet() { + if(keys == null) keys = SETS.unmodifiable(map.keySet()); + return (ORDERED_SET KEY_GENERIC_TYPE)keys; + } + + @Override + public ObjectOrderedSet ENTRY_SET() { + if(entrySet == null) entrySet = new UnmodifyableOrderedEntrySetKV_BRACES(map.ENTRY_SET()); + return (ObjectOrderedSet)entrySet; + } } /** @@ -556,15 +571,14 @@ public class MAPS public SORTED_MAP KEY_VALUE_GENERIC_TYPE tailMap(KEY_TYPE fromKey) { return MAPS.unmodifiable(map.tailMap(fromKey)); } @Override public SORTED_SET KEY_GENERIC_TYPE keySet() { return SETS.unmodifiable(map.keySet()); } - @Override public KEY_TYPE FIRST_ENTRY_KEY() { return map.FIRST_ENTRY_KEY(); } @Override - public KEY_TYPE POLL_FIRST_ENTRY_KEY() { return map.POLL_FIRST_ENTRY_KEY(); } + public KEY_TYPE POLL_FIRST_ENTRY_KEY() { throw new UnsupportedOperationException(); } @Override public KEY_TYPE LAST_ENTRY_KEY() { return map.LAST_ENTRY_KEY(); } @Override - public KEY_TYPE POLL_LAST_ENTRY_KEY() { return map.POLL_LAST_ENTRY_KEY(); } + public KEY_TYPE POLL_LAST_ENTRY_KEY() { throw new UnsupportedOperationException(); } @Override public VALUE_TYPE FIRST_ENTRY_VALUE() { return map.FIRST_ENTRY_VALUE(); } @Override @@ -628,6 +642,10 @@ public class MAPS @Override public void BULK_MERGE(MAP KEY_VALUE_GENERIC_TYPE m, VALUE_UNARY_OPERATOR VALUE_VALUE_GENERIC_TYPE mappingFunction) { throw new UnsupportedOperationException(); } @Override + public void REPLACE_VALUES(UNARY_OPERATOR KEY_VALUE_GENERIC_TYPE mappingFunction) { throw new UnsupportedOperationException(); } + @Override + public void REPLACE_VALUES(MAP KEY_VALUE_GENERIC_TYPE m) { throw new UnsupportedOperationException(); } + @Override public MAP KEY_VALUE_GENERIC_TYPE copy() { return map.copy(); } @Override public void clear() { throw new UnsupportedOperationException(); } @@ -651,6 +669,45 @@ public class MAPS } } + + /** + * The Unmodifyable Ordered Set implementation for the Unmodifyable Ordered Map implementation + * @Type(T) + * @ValueType(V) + */ + public static class UnmodifyableOrderedEntrySet KEY_VALUE_GENERIC_TYPE extends UnmodifyableEntrySet KEY_VALUE_GENERIC_TYPE implements ObjectOrderedSet + { + ObjectOrderedSet set; + + UnmodifyableOrderedEntrySet(ObjectOrderedSet c) { + super(c); + set = c; + } + + @Override + public boolean addAndMoveToFirst(MAP.Entry KEY_VALUE_GENERIC_TYPE o) { throw new UnsupportedOperationException(); } + @Override + public boolean addAndMoveToLast(MAP.Entry KEY_VALUE_GENERIC_TYPE o) { throw new UnsupportedOperationException(); } + @Override + public boolean moveToFirst(MAP.Entry KEY_VALUE_GENERIC_TYPE o) { throw new UnsupportedOperationException(); } + @Override + public boolean moveToLast(MAP.Entry KEY_VALUE_GENERIC_TYPE o) { throw new UnsupportedOperationException(); } + @Override + public ObjectOrderedSet copy() { return set.copy(); } + @Override + public ObjectBidirectionalIterator iterator() { return ObjectIterators.unmodifiable(set.iterator()); } + @Override + public ObjectBidirectionalIterator iterator(MAP.Entry KEY_VALUE_GENERIC_TYPE fromElement) { return ObjectIterators.unmodifiable(set.iterator(fromElement)); } + @Override + public MAP.Entry KEY_VALUE_GENERIC_TYPE first() { return set.first(); } + @Override + public MAP.Entry KEY_VALUE_GENERIC_TYPE pollFirst() { throw new UnsupportedOperationException(); } + @Override + public MAP.Entry KEY_VALUE_GENERIC_TYPE last() { return set.last(); } + @Override + public MAP.Entry KEY_VALUE_GENERIC_TYPE pollLast() { throw new UnsupportedOperationException(); } + } + /** * The Unmodifyable Set implementation for the Unmodifyable Map implementation * @Type(T) @@ -846,6 +903,17 @@ public class MAPS public VALUE_TYPE LAST_ENTRY_VALUE() { synchronized(mutex) { return map.LAST_ENTRY_VALUE(); } } @Override public ORDERED_MAP KEY_VALUE_GENERIC_TYPE copy() { synchronized(mutex) { return map.copy(); } } + @Override + public ORDERED_SET KEY_GENERIC_TYPE keySet() { + if(keys == null) keys = SETS.synchronize(map.keySet(), mutex); + return (ORDERED_SET KEY_GENERIC_TYPE)keys; + } + + @Override + public ObjectOrderedSet ENTRY_SET() { + if(entrySet == null) entrySet = ObjectSets.synchronize(map.ENTRY_SET(), mutex); + return (ObjectOrderedSet)entrySet; + } } /**