Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(10)

Side by Side Diff: sdk/lib/collection/splay_tree.dart

Issue 289353002: Add SetBase/SetMixin. (Closed) Base URL: https://dart.googlecode.com/svn/branches/bleeding_edge/dart
Patch Set: Updated to not use cloneEmpty Created 6 years, 7 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
« sdk/lib/collection/set.dart ('K') | « sdk/lib/collection/set.dart ('k') | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright (c) 2012, the Dart project authors. Please see the AUTHORS file 1 // Copyright (c) 2012, the Dart project authors. Please see the AUTHORS file
2 // for details. All rights reserved. Use of this source code is governed by a 2 // for details. All rights reserved. Use of this source code is governed by a
3 // BSD-style license that can be found in the LICENSE file. 3 // BSD-style license that can be found in the LICENSE file.
4 4
5 part of dart.collection; 5 part of dart.collection;
6 6
7 typedef bool _Predicate<T>(T value); 7 typedef bool _Predicate<T>(T value);
8 8
9 /** 9 /**
10 * A node in a splay tree. It holds the sorting key and the left 10 * A node in a splay tree. It holds the sorting key and the left
(...skipping 621 matching lines...) Expand 10 before | Expand all | Expand 10 after
632 * 632 *
633 * The set is based on a self-balancing binary tree. It allows most operations 633 * The set is based on a self-balancing binary tree. It allows most operations
634 * in amortized logarithmic time. 634 * in amortized logarithmic time.
635 * 635 *
636 * Elements of the set are compared using the `compare` function passed in 636 * Elements of the set are compared using the `compare` function passed in
637 * the constructor. If that is omitted, the objects are assumed to be 637 * the constructor. If that is omitted, the objects are assumed to be
638 * [Comparable], and are compared using their [Comparable.compareTo] 638 * [Comparable], and are compared using their [Comparable.compareTo]
639 * method. Non-comparable objects (including `null`) will not work as an element 639 * method. Non-comparable objects (including `null`) will not work as an element
640 * in that case. 640 * in that case.
641 */ 641 */
642 class SplayTreeSet<E> extends _SplayTree<E> with IterableMixin<E> 642 class SplayTreeSet<E> extends _SplayTree<E> with IterableMixin<E>, SetMixin<E> {
643 implements Set<E> {
644 Comparator _comparator; 643 Comparator _comparator;
645 _Predicate _validKey; 644 _Predicate _validKey;
646 645
647 /** 646 /**
648 * Create a new [SplayTreeSet] with the given compare function. 647 * Create a new [SplayTreeSet] with the given compare function.
649 * 648 *
650 * If the [compare] function is omitted, it defaults to [Comparable.compare], 649 * If the [compare] function is omitted, it defaults to [Comparable.compare],
651 * and the elements must be comparable. 650 * and the elements must be comparable.
652 * 651 *
653 * A provided `compare` function may not work on all objects. It may not even 652 * A provided `compare` function may not work on all objects. It may not even
(...skipping 22 matching lines...) Expand all
676 675
677 // From Iterable. 676 // From Iterable.
678 677
679 Iterator<E> get iterator => new _SplayTreeKeyIterator<E>(this); 678 Iterator<E> get iterator => new _SplayTreeKeyIterator<E>(this);
680 679
681 int get length => _count; 680 int get length => _count;
682 bool get isEmpty => _root == null; 681 bool get isEmpty => _root == null;
683 bool get isNotEmpty => _root != null; 682 bool get isNotEmpty => _root != null;
684 683
685 E get first { 684 E get first {
686 if (_count == 0) throw new StateError("no such element"); 685 if (_count == 0) throw IterableElementError.noElement();
687 return _first.key; 686 return _first.key;
688 } 687 }
689 688
690 E get last { 689 E get last {
691 if (_count == 0) throw new StateError("no such element"); 690 if (_count == 0) throw IterableElementError.noElement();
692 return _last.key; 691 return _last.key;
693 } 692 }
694 693
695 E get single { 694 E get single {
696 if (_count == 0) throw new StateError("no such element"); 695 if (_count == 0) throw IterableElementError.noElement();
697 if (_count > 1) throw new StateError("too many elements"); 696 if (_count > 1) throw IterableElementError.tooMany();
698 return _root.key; 697 return _root.key;
699 } 698 }
700 699
701 // From Set. 700 // From Set.
702 bool contains(Object object) { 701 bool contains(Object object) {
703 return _validKey(object) && _splay(object) == 0; 702 return _validKey(object) && _splay(object) == 0;
704 } 703 }
705 704
706 bool add(E element) { 705 bool add(E element) {
707 int compare = _splay(element); 706 int compare = _splay(element);
(...skipping 15 matching lines...) Expand all
723 } 722 }
724 } 723 }
725 } 724 }
726 725
727 void removeAll(Iterable<Object> elements) { 726 void removeAll(Iterable<Object> elements) {
728 for (Object element in elements) { 727 for (Object element in elements) {
729 if (_validKey(element)) _remove(element); 728 if (_validKey(element)) _remove(element);
730 } 729 }
731 } 730 }
732 731
733 /**
734 * Removes all elements not in [elements].
735 */
736 void retainAll(Iterable<Object> elements) { 732 void retainAll(Iterable<Object> elements) {
737 // Build a set with the same sense of equality as this set. 733 // Build a set with the same sense of equality as this set.
738 SplayTreeSet<E> retainSet = new SplayTreeSet<E>(_comparator, _validKey); 734 SplayTreeSet<E> retainSet = new SplayTreeSet<E>(_comparator, _validKey);
739 int modificationCount = _modificationCount; 735 int modificationCount = _modificationCount;
740 for (Object object in elements) { 736 for (Object object in elements) {
741 if (modificationCount != _modificationCount) { 737 if (modificationCount != _modificationCount) {
742 // The iterator should not have side effects. 738 // The iterator should not have side effects.
743 throw new ConcurrentModificationError(this); 739 throw new ConcurrentModificationError(this);
744 } 740 }
745 // Equivalent to this.contains(object). 741 // Equivalent to this.contains(object).
746 if (_validKey(object) && _splay(object) == 0) retainSet.add(_root.key); 742 if (_validKey(object) && _splay(object) == 0) retainSet.add(_root.key);
747 } 743 }
748 // Take over the elements from the retained set, if it differs. 744 // Take over the elements from the retained set, if it differs.
749 if (retainSet._count != _count) { 745 if (retainSet._count != _count) {
750 _root = retainSet._root; 746 _root = retainSet._root;
751 _count = retainSet._count; 747 _count = retainSet._count;
752 _modificationCount++; 748 _modificationCount++;
753 } 749 }
754 } 750 }
755 751
756 void _filterWhere(bool test(E element), bool removeMatching) {
757 _SplayTreeNodeIterator it = new _SplayTreeNodeIterator(this);
758 while (it.moveNext()) {
759 _SplayTreeNode node = it.current;
760 int modificationCount = _modificationCount;
761 bool matches = test(node.key);
762 if (modificationCount != _modificationCount) {
763 throw new ConcurrentModificationError(this);
764 }
765 if (matches == removeMatching) {
766 _remove(node.key);
767 it = new _SplayTreeNodeIterator.startAt(this, node.key);
768 }
769 }
770 }
771
772 void removeWhere(bool test(E element)) {
773 _filterWhere(test, true);
774 }
775
776 void retainWhere(bool test(E element)) {
777 _filterWhere(test, false);
778 }
779
780 E lookup(Object object) { 752 E lookup(Object object) {
781 if (!_validKey(object)) return null; 753 if (!_validKey(object)) return null;
782 int comp = _splay(object); 754 int comp = _splay(object);
783 if (comp != 0) return null; 755 if (comp != 0) return null;
784 return _root.key; 756 return _root.key;
785 } 757 }
786 758
787 Set<E> intersection(Set<E> other) {
788 Set<E> result = new SplayTreeSet<E>(_compare, _validKey);
789 for (E element in this) {
790 if (other.contains(element)) result.add(element);
791 }
792 return result;
793 }
794
795 Set<E> difference(Set<E> other) {
796 Set<E> result = new SplayTreeSet<E>(_compare, _validKey);
797 for (E element in this) {
798 if (!other.contains(element)) result.add(element);
799 }
800 return result;
801 }
802
803 Set<E> union(Set<E> other) {
804 return _clone()..addAll(other);
805 }
806
807 SplayTreeSet<E> _clone() { 759 SplayTreeSet<E> _clone() {
808 var set = new SplayTreeSet<E>(_compare, _validKey); 760 var set = new SplayTreeSet<E>(_comparator, _validKey);
809 set._count = _count; 761 set._count = _count;
810 set._root = _cloneNode(_root); 762 set._root = _cloneNode(_root);
811 return set; 763 return set;
812 } 764 }
813 765
814 _SplayTreeNode<E> _cloneNode(_SplayTreeNode<E> node) { 766 _SplayTreeNode<E> _cloneNode(_SplayTreeNode<E> node) {
815 if (node == null) return null; 767 if (node == null) return null;
816 return new _SplayTreeNode<E>(node.key)..left = _cloneNode(node.left) 768 return new _SplayTreeNode<E>(node.key)..left = _cloneNode(node.left)
817 ..right = _cloneNode(node.right); 769 ..right = _cloneNode(node.right);
818 } 770 }
819 771
820 bool containsAll(Iterable<Object> other) { 772 void clear() { _clear(); }
821 for (var element in other) {
822 if (!this.contains(element)) return false;
823 }
824 return true;
825 }
826 773
827 void clear() { _clear(); } 774 Set<E> toSet() => _clone();
828 } 775 }
OLDNEW
« sdk/lib/collection/set.dart ('K') | « sdk/lib/collection/set.dart ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698