/* treemap.vala * * Copyright (C) 2009-2011 Maciej Piechotka * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public * License as published by the Free Software Foundation; either * version 2.1 of the License, or (at your option) any later version. * This library is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * Lesser General Public License for more details. * You should have received a copy of the GNU Lesser General Public * License along with this library; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA * * Author: * Maciej Piechotka */ using GLib; /** * Left-leaning red-black tree implementation of the {@link Map} interface. * * This implementation is especially well designed for large quantity of * data. The (balanced) tree implementation insure that the set and get * methods are in logarithmic complexity. * * @see HashMap */ public class Gee.TreeMap : Gee.AbstractBidirSortedMap { /** * {@inheritDoc} */ public override int size { get { return _size; } } public override bool read_only { get { return false; } } /** * {@inheritDoc} */ public override Set keys { owned get { var keys = _keys; if (_keys == null) { keys = new KeySet (this); _keys = keys; keys.add_weak_pointer ((void**) (&_keys)); } return keys; } } /** * {@inheritDoc} */ public override Collection values { owned get { var values = _values; if (_values == null) { values = new ValueCollection (this); _values = values; values.add_weak_pointer ((void**) (&_values)); } return values; } } /** * {@inheritDoc} */ public override Set> entries { owned get { var entries = _entries; if (_entries == null) { entries = new EntrySet (this); _entries = entries; entries.add_weak_pointer ((void**) (&_entries)); } return entries; } } /** * The keys' comparator function. */ [CCode (notify = false)] public CompareDataFunc key_compare_func { private set; get; } /** * The values' equality testing function. */ [CCode (notify = false)] public EqualDataFunc value_equal_func { private set; get; } private int _size = 0; private weak SortedSet _keys; private weak Collection _values; private weak SortedSet> _entries; /** * Constructs a new, empty tree map sorted according to the specified * comparator function. * * If not provided, the functions parameters are requested to the * {@link Functions} function factory methods. * * @param key_compare_func an optional key comparator function * @param value_equal_func an optional values equality testing function */ public TreeMap (owned CompareDataFunc? key_compare_func = null, owned EqualDataFunc? value_equal_func = null) { if (key_compare_func == null) { key_compare_func = Functions.get_compare_func_for (typeof (K)); } if (value_equal_func == null) { value_equal_func = Functions.get_equal_func_for (typeof (V)); } this.key_compare_func = key_compare_func; this.value_equal_func = value_equal_func; } ~TreeMap () { clear (); } private void rotate_right (ref Node root) { Node pivot = (owned) root.left; pivot.color = root.color; root.color = Node.Color.RED; root.left = (owned) pivot.right; pivot.right = (owned) root; root = (owned) pivot; } private void rotate_left (ref Node root) { Node pivot = (owned) root.right; pivot.color = root.color; root.color = Node.Color.RED; root.right = (owned) pivot.left; pivot.left = (owned) root; root = (owned) pivot; } private bool is_red (Node? n) { return n != null && n.color == Node.Color.RED; } private bool is_black (Node? n) { return n == null || n.color == Node.Color.BLACK; } /** * {@inheritDoc} */ public override bool has_key (K key) { weak Node? cur = root; while (cur != null) { int res = key_compare_func (key, cur.key); if (res == 0) { return true; } else if (res < 0) { cur = cur.left; } else { cur = cur.right; } } return false; } /** * {@inheritDoc} */ public override bool has (K key, V value) { V? own_value = get (key); return (own_value != null && value_equal_func (own_value, value)); } /** * {@inheritDoc} */ public override V? get (K key) { weak Node? cur = root; while (cur != null) { int res = key_compare_func (key, cur.key); if (res == 0) { return cur.value; } else if (res < 0) { cur = cur.left; } else { cur = cur.right; } } return null; } private bool set_to_node (ref Node? node, K key, V value, out V? old_value, Node? prev, Node? next) { if (node == null) { old_value = null; node = new Node (key, value, prev, next); if (prev == null) { first = node; } if (next == null) { last = node; } _size++; return true; } int cmp = key_compare_func (key, node.key); bool changed; if (cmp == 0) { if (value_equal_func (value, node.value)) { old_value = null; changed = false; } else { old_value = (owned) node.value; node.value = value; changed = true; } } else if (cmp < 0) { changed = set_to_node (ref node.left, key, value, out old_value, node.prev, node); } else { changed = set_to_node (ref node.right, key, value, out old_value, node, node.next); } fix_up (ref node); return changed; } /** * {@inheritDoc} */ public override void set (K key, V value) { V old_value; set_to_node (ref root, key, value, out old_value, null, null); root.color = Node.Color.BLACK; stamp++; } private void move_red_left (ref Node root) { root.flip (); if (is_red (root.right.left)) { rotate_right (ref root.right); rotate_left (ref root); root.flip (); } } private void move_red_right (ref Node root) { root.flip (); if (is_red (root.left.left)) { rotate_right (ref root); root.flip (); } } private void fix_removal (ref Node node, out K? key = null, out V? value) { Node n = (owned) node; key = (owned) n.key; value = (owned) n.value; if (n.prev != null) { n.prev.next = n.next; } else { first = n.next; } if (n.next != null) { n.next.prev = n.prev; } else { last = n.next; } n.value = null; node = null; _size--; } private void remove_minimal (ref Node node, out K key, out V value) { if (node.left == null) { fix_removal (ref node, out key, out value); return; } if (is_black (node.left) && is_black (node.left.left)) { move_red_left (ref node); } remove_minimal (ref node.left, out key, out value); fix_up (ref node); } private bool remove_from_node (ref Node? node, K key, out V? value, out unowned Node? prev = null, out unowned Node? next = null) { if (node == null) { value = null; next = null; prev = null; return false; } else if (key_compare_func (key, node.key) < 0) { weak Node left = node.left; if (left == null) { value = null; next = null; prev = null; return false; } if (node.left != null && is_black (left) && is_black (left.left)) { move_red_left (ref node); } bool r = remove_from_node (ref node.left, key, out value, out prev, out next); fix_up (ref node); return r; } else { if (is_red (node.left)) { rotate_right (ref node); } weak Node? r = node.right; if (key_compare_func (key, node.key) == 0 && r == null) { prev = node.prev; next = node.next; fix_removal (ref node, null, out value); return true; } if (is_black (r) && r != null && is_black (r.left)) { move_red_right (ref node); } if (key_compare_func (key, node.key) == 0) { value = (owned) node.value; prev = node.prev; next = node; remove_minimal (ref node.right, out node.key, out node.value); fix_up (ref node); return true; } else { bool re = remove_from_node (ref node.right, key, out value, out prev, out next); fix_up (ref node); return re; } } } private void fix_up (ref Node node) { if (is_black (node.left) && is_red (node.right)) { rotate_left (ref node); } if (is_red (node.left) && is_red (node.left.left)) { rotate_right (ref node); } if (is_red (node.left) && is_red (node.right)) { node.flip (); } } /** * {@inheritDoc} */ public override bool unset (K key, out V? value = null) { bool b = remove_from_node (ref root, key, out value); if (root != null) { root.color = Node.Color.BLACK; } stamp++; return b; } private inline void clear_subtree (owned Node node) { node.key = null; node.value = null; if (node.left != null) clear_subtree ((owned) node.left); if (node.right != null) clear_subtree ((owned) node.right); } /** * {@inheritDoc} */ public override void clear () { if (root != null) { clear_subtree ((owned) root); first = last = null; } _size = 0; stamp++; } /** * {@inheritDoc} */ public override SortedMap head_map (K before) { return new SubMap (this, new Range.head (this, before)); } /** * {@inheritDoc} */ public override SortedMap tail_map (K after) { return new SubMap (this, new Range.tail (this, after)); } /** * {@inheritDoc} */ public override SortedMap sub_map (K after, K before) { return new SubMap (this, new Range (this, after, before)); } /** * {@inheritDoc} */ public override SortedSet ascending_keys { owned get { var keys = _keys; if (_keys == null) { keys = new KeySet (this); _keys = keys; keys.add_weak_pointer (&_keys); } return keys; } } /** * {@inheritDoc} */ public override SortedSet> ascending_entries { owned get { var entries = _entries; if (_entries == null) { entries = new EntrySet (this); _entries = entries; entries.add_weak_pointer (&_entries); } return entries; } } /** * {@inheritDoc} */ public override Gee.MapIterator map_iterator () { return new MapIterator (this); } /** * {@inheritDoc} */ public override Gee.BidirMapIterator bidir_map_iterator () { return new MapIterator (this); } [Compact] private class Node { public enum Color { RED, BLACK; public Color flip () { if (this == RED) { return BLACK; } else { return RED; } } } public Node (owned K key, owned V value, Node? prev, Node? next) { this.key = (owned) key; this.value = (owned) value; this.color = Color.RED; this.prev = prev; this.next = next; if (prev != null) { prev.next = this; } if (next != null) { next.prev = this; } } public void flip () { color = color.flip (); if (left != null) { left.color = left.color.flip (); } if (right != null) { right.color = right.color.flip (); } } public K key; public V value; public Color color; public Node? left; public Node? right; public weak Node? prev; public weak Node? next; public unowned Map.Entry? entry; } private Node? root = null; private weak Node? first = null; private weak Node? last = null; private int stamp = 0; private inline K min (K a, K b) { return key_compare_func (a, b) <= 0 ? a : b; } private inline K max (K a, K b) { return key_compare_func (a, b) > 0 ? a : b; } private inline unowned Node? find_node (K key) { unowned Node? cur = root; while (cur != null) { int res = key_compare_func (key, cur.key); if (res == 0) { return cur; } else if (res < 0) { cur = cur.left; } else { cur = cur.right; } } return null; } private inline unowned Node? find_nearest (K key) { unowned Node? cur = root; while (cur != null) { int res = key_compare_func (key, cur.key); if (res == 0) { return cur; } else if (res < 0) { if (cur.left == null) return cur; cur = cur.left; } else { if (cur.right == null) return cur; cur = cur.right; } } return null; } private class Entry : Map.Entry { private unowned Node _node; public static Map.Entry entry_for (Node node) { Map.Entry result = node.entry; if (result == null) { result = new Entry (node); node.entry = result; result.add_weak_pointer ((void**) (&node.entry)); } return result; } public Entry (Node node) { _node = node; } public override K key { get { return _node.key; } } public override V value { get { return _node.value; } set { _node.value = value; } } public override bool read_only { get { return false; } } } private inline unowned Node? find_lower (K key) { unowned Node? node = find_nearest (key); if (node == null) return null; return key_compare_func (key, node.key) <= 0 ? node.prev : node; } private inline unowned Node? find_higher (K key) { unowned Node? node = find_nearest (key); if (node == null) return null; return key_compare_func (key, node.key) >= 0 ? node.next : node; } private inline unowned Node? find_floor (K key) { unowned Node? node = find_nearest (key); if (node == null) return null; return key_compare_func (key, node.key) < 0 ? node.prev : node; } private inline unowned Node? find_ceil (K key) { unowned Node? node = find_nearest (key); if (node == null) return null; return key_compare_func (key, node.key) > 0 ? node.next : node; } private inline K? lift_null_key (Node? node) { return node != null ? node.key : null; } private class Range { public Range (TreeMap map, K after, K before) { this.map = map; if (map.key_compare_func (after, before) < 0) { this.after = after; this.before = before; type = RangeType.BOUNDED; } else { type = RangeType.EMPTY; } } public Range.head (TreeMap map, K before) { this.map = map; this.before = before; type = RangeType.HEAD; } public Range.tail (TreeMap map, K after) { this.map = map; this.after = after; type = RangeType.TAIL; } public Range.empty (TreeMap map) { this.map = map; type = RangeType.EMPTY; } public Range cut_head (K after) { switch (type) { case RangeType.HEAD: return new Range (map, after, before); case RangeType.TAIL: return new Range.tail (map, map.max (after, this.after)); case RangeType.EMPTY: return this; case RangeType.BOUNDED: var _after = map.max (after, this.after); return new Range (map, _after, before); default: assert_not_reached (); } } public Range cut_tail (K before) { switch (type) { case RangeType.HEAD: return new Range.head (map, map.min (before, this.before)); case RangeType.TAIL: return new Range (map, after, before); case RangeType.EMPTY: return this; case RangeType.BOUNDED: var _before = map.min (before, this.before); return new Range (map, after, _before); default: assert_not_reached (); } } public Range cut (K after, K before) { if (type == RangeType.EMPTY) return this; var _before = (type == RangeType.HEAD || type == RangeType.BOUNDED) ? map.min (before, this.before) : before; var _after = (type == RangeType.TAIL || type == RangeType.BOUNDED) ? map.max (after, this.after) : after; return new Range (map, _after, _before); } public bool in_range (K key) { return type == RangeType.EMPTY ? false : compare_range(key) == 0; } public int compare_range (K key) { switch (type) { case RangeType.HEAD: return map.key_compare_func (key, before) < 0 ? 0 : 1; case RangeType.TAIL: return map.key_compare_func (key, after) >= 0 ? 0 : -1; case RangeType.EMPTY: return 0; // For simplicity - please make sure it does not break anything case RangeType.BOUNDED: return map.key_compare_func (key, after) >= 0 ? (map.key_compare_func (key, before) < 0 ? 0 : 1) : -1; default: assert_not_reached (); } } public bool empty_submap () { switch (type) { case RangeType.HEAD: return map.first == null || !in_range (map.first.key); case RangeType.TAIL: return map.last == null || !in_range (map.last.key); case RangeType.EMPTY: return true; case RangeType.BOUNDED: return first () == null; default: assert_not_reached (); } } public unowned Node? first () { switch (type) { case RangeType.EMPTY: return null; case RangeType.HEAD: return map.first; default: return map.find_floor (after); } } public unowned Node? last () { switch (type) { case RangeType.EMPTY: return null; case RangeType.TAIL: return map.last; default: return map.find_lower (before); } } private new TreeMap map; private K after; private K before; private RangeType type; } private enum RangeType { HEAD, TAIL, EMPTY, BOUNDED } private class SubMap : AbstractBidirSortedMap { public override int size { get { return keys.size; } } public bool is_empty { get { return keys.is_empty; } } public SubMap (TreeMap map, Range range) { this.map = map; this.range = range; } private weak SortedSet? _keys; public override Set keys { owned get { var keys = _keys; if (_keys == null) { keys = new SubKeySet (map, range); _keys = keys; keys.add_weak_pointer(&_keys); } return keys; } } private weak Collection? _values; public override Collection values { owned get { var values = _values; if (_values == null) { values = new SubValueCollection (map, range); _values = values; values.add_weak_pointer(&_values); } return values; } } private weak SortedSet>? _entries; public override Set> entries { owned get { var entries = _entries; if (_entries == null) { entries = new SubEntrySet (map, range); _entries = entries; entries.add_weak_pointer(&_entries); } return entries; } } public override bool read_only { get { return true; } } public override bool has_key (K key) { return range.in_range (key) && map.has_key (key); } public override bool has (K key, V value) { return range.in_range (key) && map.has (key, value); } public override new V? get (K key) { return range.in_range (key) ? map.get (key) : null; } public override void set (K key, V value) { if (range.in_range (key)) map.set (key, value); } public override bool unset (K key, out V? value = null) { value = null; return range.in_range (key) && map.unset (key, out value); } public override void clear () { for (var iterator = map_iterator (); iterator.next ();) iterator.unset (); } public override Gee.MapIterator map_iterator () { return new SubMapIterator (map, range); } public override BidirMapIterator bidir_map_iterator () { return new SubMapIterator (map, range); } public override SortedMap head_map (K before) { return new SubMap (map, range.cut_tail (before)); } public override SortedMap tail_map (K after) { return new SubMap (map, range.cut_head (after)); } public override SortedMap sub_map (K after, K before) { return new SubMap (map, range.cut (after, before)); } public override SortedSet ascending_keys { owned get { var keys = _keys; if (_keys == null) { keys = new SubKeySet (map, range); _keys = keys; keys.add_weak_pointer(&_keys); } return keys; } } public override SortedSet ascending_entries { owned get { var entries = _entries; if (_entries == null) { entries = new SubEntrySet (map, range); _entries = entries; entries.add_weak_pointer(&_entries); } return _entries; } } private TreeMap map; private Range range; } private class KeySet : AbstractBidirSortedSet { private TreeMap _map; public KeySet (TreeMap map) { _map = map; } public override Iterator iterator () { return new KeyIterator (_map); } public override int size { get { return _map.size; } } public override bool read_only { get { return true; } } public override bool add (K key) { assert_not_reached (); } public override void clear () { assert_not_reached (); } public override bool remove (K key) { assert_not_reached (); } public override bool contains (K key) { return _map.has_key (key); } public override K first () { assert (_map.first != null); return _map.first.key; } public override K last () { assert (_map.last != null); return _map.last.key; } public override BidirIterator bidir_iterator () { return new KeyIterator (_map); } public override SortedSet head_set (K before) { return new SubKeySet (_map, new Range.head (_map, before)); } public override SortedSet tail_set (K after) { return new SubKeySet (_map, new Range.tail (_map, after)); } public override SortedSet sub_set (K after, K before) { return new SubKeySet (_map, new Range (_map, after, before)); } public override Iterator? iterator_at (K item) { weak Node? node = _map.find_node (item); if (node == null) return null; return new KeyIterator.pointing (_map, node); } public override K? lower (K item) { return _map.lift_null_key (_map.find_lower (item)); } public override K? higher (K item) { return _map.lift_null_key (_map.find_higher (item)); } public override K? floor (K item) { return _map.lift_null_key (_map.find_floor (item)); } public override K? ceil (K item) { return _map.lift_null_key (_map.find_ceil (item)); } } private class SubKeySet : AbstractBidirSortedSet { [CCode (notify = false)] public TreeMap map { private set; get; } [CCode (notify = false)] public Range range { private set; get; } public SubKeySet (TreeMap map, Range range) { this.map = map; this.range = range; } public override Iterator iterator () { return new SubKeyIterator (map, range); } public override int size { get { var i = 0; Gee.Iterator iterator = iterator (); while (iterator.next ()) i++; return i; } } public override bool read_only { get { return true; } } public bool is_empty { get { return range.empty_submap (); } } public override bool add (K key) { assert_not_reached (); } public override void clear () { assert_not_reached (); } public override bool remove (K key) { assert_not_reached (); } public override bool contains (K key) { return range.in_range(key) && map.has_key (key); } public override BidirIterator bidir_iterator () { return new SubKeyIterator (map, range); } public override K first () { weak Node? _first = range.first (); assert (_first != null); return _first.key; } public override K last () { weak Node? _last = range.last (); assert (_last != null); return _last.key; } public override SortedSet head_set (K before) { return new SubKeySet (map, range.cut_tail (before)); } public override SortedSet tail_set (K after) { return new SubKeySet (map, range.cut_head (after)); } public override SortedSet sub_set (K after, K before) { return new SubKeySet (map, range.cut (after, before)); } public override Iterator? iterator_at (K key) { if (!range.in_range (key)) return null; weak Node? n = map.find_node (key); if (n == null) return null; return new SubKeyIterator.pointing (map, range, n); } public override K? lower (K key) { var res = range.compare_range (key); if (res > 0) return last (); var l = map.lift_null_key (map.find_lower (key)); return l != null && range.in_range (l) ? l : null; } public override K? higher (K key) { var res = range.compare_range (key); if (res < 0) return first (); var h = map.lift_null_key (map.find_higher (key)); return h != null && range.in_range (h) ? h : null; } public override K? floor (K key) { var res = range.compare_range (key); if (res > 0) return last (); var l = map.lift_null_key (map.find_floor (key)); return l != null && range.in_range (l) ? l : null; } public override K? ceil (K key) { var res = range.compare_range (key); if (res < 0) return first (); var h = map.lift_null_key (map.find_ceil (key)); return h != null && range.in_range (h) ? h : null; } } private class ValueCollection : AbstractCollection { private TreeMap _map; public ValueCollection (TreeMap map) { _map = map; } public override Iterator iterator () { return new ValueIterator (_map); } public override int size { get { return _map.size; } } public override bool read_only { get { return true; } } public override bool add (V key) { assert_not_reached (); } public override void clear () { assert_not_reached (); } public override bool remove (V key) { assert_not_reached (); } public override bool contains (V key) { Iterator it = iterator (); while (it.next ()) { if (_map.value_equal_func (key, it.get ())) { return true; } } return false; } } private class SubValueCollection : AbstractCollection { [CCode (notify = false)] public TreeMap map { private set; get; } [CCode (notify = false)] public Range range { private set; get; } public SubValueCollection (TreeMap map, Range range) { this.map = map; this.range = range; } public override Iterator iterator () { return new SubValueIterator (map, range); } public override bool read_only { get { return true; } } public override int size { get { var i = 0; Gee.Iterator iterator = iterator (); while (iterator.next ()) i++; return i; } } public bool is_empty { get { return range.empty_submap (); } } public override bool add (V key) { assert_not_reached (); } public override void clear () { assert_not_reached (); } public override bool remove (V key) { assert_not_reached (); } public override bool contains (V key) { Iterator it = iterator (); while (it.next ()) { if (map.value_equal_func (key, it.get ())) { return true; } } return false; } } private class EntrySet : AbstractBidirSortedSet> { private TreeMap _map; public EntrySet (TreeMap map) { _map = map; } public override Iterator> iterator () { return new EntryIterator (_map); } public override int size { get { return _map.size; } } public override bool read_only { get { return true; } } public override bool add (Map.Entry entry) { assert_not_reached (); } public override void clear () { assert_not_reached (); } public override bool remove (Map.Entry entry) { assert_not_reached (); } public override bool contains (Map.Entry entry) { return _map.has (entry.key, entry.value); } public override Map.Entry/*?*/ first () { assert (_map.first != null); return Entry.entry_for (_map.first); } public override Map.Entry/*?*/ last () { assert (_map.last != null); return Entry.entry_for (_map.last); } public override BidirIterator> bidir_iterator () { return new EntryIterator (_map); } public override SortedSet> head_set (Map.Entry before) { return new SubEntrySet (_map, new Range.head (_map, before.key)); } public override SortedSet> tail_set (Map.Entry after) { return new SubEntrySet (_map, new Range.tail (_map, after.key)); } public override SortedSet sub_set (Map.Entry after, Map.Entry before) { return new SubEntrySet (_map, new Range (_map, after.key, before.key)); } public override Iterator>? iterator_at (Map.Entry item) { weak Node? node = _map.find_node (item.key); if (node == null || !_map.value_equal_func (node.value, item.value)) return null; return new EntryIterator.pointing (_map, node); } public override Map.Entry/*?*/ lower (Map.Entry item) { weak Node? l = _map.find_lower (item.key); return l != null ? Entry.entry_for (l) : null; } public override Map.Entry/*?*/ higher (Map.Entry item) { weak Node? l = _map.find_higher (item.key); return l != null ? Entry.entry_for (l) : null; } public override Map.Entry/*?*/ floor (Map.Entry item) { weak Node? l = _map.find_floor (item.key); return l != null ? Entry.entry_for (l) : null; } public override Map.Entry/*?*/ ceil (Map.Entry item) { weak Node? l = _map.find_ceil (item.key); return l != null ? Entry.entry_for (l) : null; } } private class SubEntrySet : AbstractBidirSortedSet> { [CCode (notify = false)] public TreeMap map { private set; get; } [CCode (notify = false)] public Range range { private set; get; } public SubEntrySet (TreeMap map, Range range) { this.map = map; this.range = range; } public override Iterator> iterator () { return new SubEntryIterator (map, range); } public override int size { get { var i = 0; Gee.Iterator> iterator = iterator (); while (iterator.next ()) i++; return i; } } public override bool read_only { get { return true; } } public bool is_empty { get { return range.empty_submap (); } } public override bool add (Map.Entry entry) { assert_not_reached (); } public override void clear () { assert_not_reached (); } public override bool remove (Map.Entry entry) { assert_not_reached (); } public override bool contains (Map.Entry entry) { return range.in_range(entry.key) && map.has (entry.key, entry.value); } public override BidirIterator bidir_iterator () { return new SubEntryIterator (map, range); } public override Map.Entry first () { weak Node? _first = range.first (); assert (_first != null); return Entry.entry_for (_first); } public override Map.Entry last () { weak Node? _last = range.last (); assert (_last != null); return Entry.entry_for (_last); } public override SortedSet head_set (Map.Entry before) { return new SubEntrySet (map, range.cut_tail (before.key)); } public override SortedSet tail_set (Map.Entry after) { return new SubEntrySet (map, range.cut_head (after.key)); } public override SortedSet sub_set (Map.Entry after, Map.Entry before) { return new SubEntrySet (map, range.cut (after.key, before.key)); } public override Iterator>? iterator_at (Map.Entry entry) { if (!range.in_range (entry.key)) return null; weak Node? n = map.find_node (entry.key); if (n == null || !map.value_equal_func (n.value, entry.value)) return null; return new SubEntryIterator.pointing (map, range, n); } public override Map.Entry/*?*/ lower (Map.Entry entry) { var res = range.compare_range (entry.key); if (res > 0) return last (); weak Node? l = map.find_lower (entry.key); return l != null && range.in_range (l.key) ? Entry.entry_for (l) : null; } public override Map.Entry/*?*/ higher (Map.Entry entry) { var res = range.compare_range (entry.key); if (res < 0) return first (); weak Node? h = map.find_higher (entry.key); return h != null && range.in_range (h.key) ? Entry.entry_for (h) : null; } public override Map.Entry/*?*/ floor (Map.Entry entry) { var res = range.compare_range (entry.key); if (res > 0) return last (); weak Node? l = map.find_floor (entry.key); return l != null && range.in_range (l.key) ? Entry.entry_for (l) : null; } public override Map.Entry/*?*/ ceil (Map.Entry entry) { var res = range.compare_range (entry.key); if (res < 0) return first (); weak Node? h = map.find_ceil (entry.key); return h != null && range.in_range (h.key) ? Entry.entry_for (h) : null; } } private class NodeIterator : Object { protected TreeMap _map; // concurrent modification protection protected int stamp; protected bool started = false; internal weak Node? current; protected weak Node? _next; protected weak Node? _prev; public NodeIterator (TreeMap map) { _map = map; this.stamp = _map.stamp; } public NodeIterator.pointing (TreeMap map, Node current) { _map = map; stamp = _map.stamp; this.current = current; } public bool next () { assert (stamp == _map.stamp); if (current != null) { if (current.next != null) { current = current.next; return true; } else { return false; } } else if (_next == null && _prev == null) { current = _map.first; started = true; return current != null; } else { current = _next; if (current != null) { _next = null; _prev = null; } return current != null; } } public bool has_next () { assert (stamp == _map.stamp); return (current == null && _next == null && _prev == null && _map.first != null) || (current == null && _next != null) || (current != null && current.next != null); } public bool first () { assert (stamp == _map.stamp); current = _map.first; _next = null; _prev = null; return current != null; // on false it is null anyway } public bool previous () { assert (stamp == _map.stamp); if (current != null) { if (current.prev != null) { current = current.prev; return true; } else { return false; } } else { if (_prev != null) { current = _prev; _next = null; _prev = null; return true; } else { return false; } } } public bool has_previous () { assert (stamp == _map.stamp); return (current == null && _prev != null) || (current != null && current.prev != null); } public bool last () { assert (stamp == _map.stamp); current = _map.last; _next = null; _prev = null; return current != null; // on false it is null anyway } public void remove () { assert_not_reached (); } public void unset () { assert (stamp == _map.stamp); assert (current != null); V value; bool success = _map.remove_from_node (ref _map.root, current.key, out value, out _prev, out _next); assert (success); if (_map.root != null) _map.root.color = Node.Color.BLACK; current = null; stamp++; _map.stamp++; assert (stamp == _map.stamp); } public virtual bool read_only { get { return true; } } public bool valid { get { return current != null; } } internal unowned Node? safe_next_get () { return (current != null) ? current.next : _next; } internal unowned Node? safe_previous_get () { return (current != null) ? current.prev : _prev; } } private class SubNodeIterator : Object { public SubNodeIterator (TreeMap map, Range range) { _map = map; this.range = range; } public SubNodeIterator.pointing (TreeMap map, Range range, Node node) { _map = map; this.range = range; this.iterator = new NodeIterator.pointing (_map, node); } public bool next () { if (iterator != null) { weak Node? node= iterator.safe_next_get (); if (node != null && range.in_range (node.key)) { assert (iterator.next ()); return true; } else { return false; } } else { return first (); } } public bool has_next () { if (iterator != null) { weak Node? node = iterator.safe_next_get (); return node != null && range.in_range (node.key); } else { return range.first () != null; } } public virtual bool first () { weak Node? node = range.first (); if (node == null) return false; iterator = iterator_pointing_at (node); return true; } public bool previous () { if (iterator == null) return false; weak Node? node; if ((node = iterator.safe_previous_get ()) != null && range.in_range (node.key)) { assert (iterator.previous ()); return true; } else { return false; } } public bool has_previous () { if (iterator == null) return false; weak Node? node; return (node = iterator.safe_previous_get ()) != null && range.in_range (node.key); } public virtual bool last () { weak Node? node = range.last (); if (node == null) return false; iterator = iterator_pointing_at (node); return true; } public void remove () { assert (valid); iterator.remove (); } public void unset () { assert (valid); iterator.unset (); } public virtual bool read_only { get { return true; } } public bool valid { get { return iterator != null && iterator.valid; } } protected virtual NodeIterator iterator_pointing_at (Node node) { return new NodeIterator.pointing (_map, node); } protected new TreeMap _map; protected Range range; protected NodeIterator? iterator = null; } private class KeyIterator : NodeIterator, Traversable, Gee.Iterator, BidirIterator { public KeyIterator (TreeMap map) { base (map); } public KeyIterator.pointing (TreeMap map, Node current) { base.pointing (map, current); } public new K get () { assert (stamp == _map.stamp); assert (current != null); return current.key; } public bool foreach (ForallFunc f) { if (current != null) { if (!f (current.key)) { return false; } current = current.next; } else if (_next == null) { current = _map.first; started = true; } else { current = _next; if (current != null) { _next = null; _prev = null; } } for (; current != null; current = current.next) { if (!f (current.key)) { return false; } } return true; } } private class SubKeyIterator : SubNodeIterator, Traversable, Gee.Iterator, BidirIterator { public SubKeyIterator (TreeMap map, Range range) { base (map, range); } public SubKeyIterator.pointing (TreeMap map, Range range, Node node) { base.pointing (map, range, node); } public new K get () { assert (valid); return iterator.current.key; } public bool foreach (ForallFunc f) { if (valid) { if (!f (iterator.current.key)) { return false; } } while (iterator.next ()) { if (!f (iterator.current.key)) { return false; } } return true; } } private class ValueIterator : NodeIterator, Traversable, Gee.Iterator, Gee.BidirIterator { public ValueIterator (TreeMap map) { base (map); } public ValueIterator.pointing (TreeMap map, Node current) { base.pointing (map, current); } public new V get () { assert (stamp == _map.stamp); assert (valid); return current.value; } public bool foreach (ForallFunc f) { if (current != null) { if (!f (current.value)) { return false; } current = current.next; } else if (_next == null) { current = _map.first; started = true; } else { current = _next; if (current != null) { _next = null; _prev = null; } } for (; current != null; current = current.next) { if (!f (current.value)) { return false; } } return true; } } private class SubValueIterator : SubNodeIterator, Traversable, Gee.Iterator, BidirIterator { public SubValueIterator (TreeMap map, Range range) { base (map, range); } public SubValueIterator.pointing (TreeMap map, Range range, Node node) { base.pointing (map, range, node); } public new V get () { assert (valid); return iterator.current.value; } public bool foreach (ForallFunc f) { if (valid) { if (!f (iterator.current.key)) { return false; } } while (iterator.next ()) { if (!f (iterator.current.key)) { return false; } } return true; } } private class EntryIterator : NodeIterator, Traversable>, Gee.Iterator>, Gee.BidirIterator> { public EntryIterator (TreeMap map) { base (map); } public EntryIterator.pointing (TreeMap map, Node node) { base.pointing (map, node); } public new Map.Entry get () { assert (stamp == _map.stamp); assert (valid); return Entry.entry_for (current); } public new void remove () { unset (); } public bool foreach (ForallFunc> f) { if (current != null) { if (!f (Entry.entry_for (current))) { return false; } current = current.next; } else if (_next == null) { current = _map.first; started = true; } else { current = _next; if (current != null) { _next = null; _prev = null; } } for (; current != null; current = current.next) { if (!f (Entry.entry_for (current))) { return false; } } return true; } } private class SubEntryIterator : SubNodeIterator, Traversable>, Gee.Iterator>, Gee.BidirIterator> { public SubEntryIterator (TreeMap map, Range range) { base (map, range); } public SubEntryIterator.pointing (TreeMap map, Range range, Node node) { base.pointing (map, range, node); } public new Map.Entry get () { assert (iterator != null); return Entry.entry_for (iterator.current); } public new void remove () { unset (); } public bool foreach (ForallFunc> f) { if (valid) { if (!f (Entry.entry_for (iterator.current))) { return false; } } while (iterator.next ()) { if (!f (Entry.entry_for (iterator.current))) { return false; } } return true; } } private class MapIterator : NodeIterator, Gee.MapIterator, BidirMapIterator { public MapIterator (TreeMap map) { base (map); } public K get_key () { assert (stamp == _map.stamp); assert (valid); return current.key; } public V get_value () { assert (stamp == _map.stamp); assert (valid); return current.value; } public void set_value (V value) { assert (stamp == _map.stamp); assert (valid); current.value = value; } public override bool read_only { get { return false; } } public bool mutable { get { return true; } } } private class SubMapIterator : SubNodeIterator, Gee.MapIterator, BidirMapIterator { public SubMapIterator (TreeMap map, Range range) { base (map, range); } public K get_key () { assert (valid); return iterator.current.key; } public V get_value () { assert (valid); return iterator.current.value; } public void set_value (V value) { assert (valid); iterator.current.value = value; } public override bool read_only { get { return false; } } public bool mutable { get { return true; } } } }