add difference and symmetric_difference to Set
This commit is contained in:
parent
42cafcee2c
commit
99eb4ddddd
3 changed files with 88 additions and 17 deletions
|
|
@ -75,4 +75,10 @@ pub trait Set<T>: Mutable {
|
|||
|
||||
/// Return true if the set is a superset of another
|
||||
pure fn is_superset(&self, other: &self) -> bool;
|
||||
|
||||
/// Visit the values representing the difference
|
||||
pure fn difference(&self, other: &self, f: fn(&T) -> bool);
|
||||
|
||||
/// Visit the values representing the symmetric difference
|
||||
pure fn symmetric_difference(&self, other: &self, f: fn(&T) -> bool);
|
||||
}
|
||||
|
|
|
|||
|
|
@ -469,6 +469,22 @@ pub mod linear {
|
|||
pure fn is_superset(&self, other: &LinearSet<T>) -> bool {
|
||||
other.is_subset(self)
|
||||
}
|
||||
|
||||
/// Visit the values representing the difference
|
||||
pure fn difference(&self, other: &LinearSet<T>, f: fn(&T) -> bool) {
|
||||
for self.each |v| {
|
||||
if !other.contains(v) {
|
||||
if !f(v) { return; }
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// Visit the values representing the symmetric difference
|
||||
pure fn symmetric_difference(&self, other: &LinearSet<T>,
|
||||
f: fn(&T) -> bool) {
|
||||
self.difference(other, f);
|
||||
other.difference(self, f);
|
||||
}
|
||||
}
|
||||
|
||||
pub impl <T: Hash IterBytes Eq> LinearSet<T> {
|
||||
|
|
@ -681,4 +697,53 @@ mod test_set {
|
|||
assert !b.is_subset(&a);
|
||||
assert b.is_superset(&a);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn test_difference() {
|
||||
let mut a = linear::LinearSet::new();
|
||||
let mut b = linear::LinearSet::new();
|
||||
|
||||
assert a.insert(1);
|
||||
assert a.insert(3);
|
||||
assert a.insert(5);
|
||||
assert a.insert(9);
|
||||
assert a.insert(11);
|
||||
|
||||
assert b.insert(3);
|
||||
assert b.insert(9);
|
||||
|
||||
let mut i = 0;
|
||||
let expected = [1, 5, 11];
|
||||
for a.difference(&b) |x| {
|
||||
assert vec::contains(expected, x);
|
||||
i += 1
|
||||
}
|
||||
assert i == expected.len();
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn test_symmetric_difference() {
|
||||
let mut a = linear::LinearSet::new();
|
||||
let mut b = linear::LinearSet::new();
|
||||
|
||||
assert a.insert(1);
|
||||
assert a.insert(3);
|
||||
assert a.insert(5);
|
||||
assert a.insert(9);
|
||||
assert a.insert(11);
|
||||
|
||||
assert b.insert(-2);
|
||||
assert b.insert(3);
|
||||
assert b.insert(9);
|
||||
assert b.insert(14);
|
||||
assert b.insert(22);
|
||||
|
||||
let mut i = 0;
|
||||
let expected = [-2, 1, 5, 11, 14, 22];
|
||||
for a.symmetric_difference(&b) |x| {
|
||||
assert vec::contains(expected, x);
|
||||
i += 1
|
||||
}
|
||||
assert i == expected.len();
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -29,10 +29,10 @@ use core::prelude::*;
|
|||
// range search - O(log n) retrieval of an iterator from some key
|
||||
|
||||
// (possibly) implement the overloads Python does for sets:
|
||||
// * union: |
|
||||
// * intersection: &
|
||||
// * difference: -
|
||||
// * symmetric difference: ^
|
||||
// * union: |
|
||||
// These would be convenient since the methods work like `each`
|
||||
|
||||
pub struct TreeMap<K, V> {
|
||||
|
|
@ -355,22 +355,6 @@ impl <T: Ord> TreeSet<T>: Set<T> {
|
|||
}
|
||||
true
|
||||
}
|
||||
}
|
||||
|
||||
impl <T: Ord> TreeSet<T> {
|
||||
/// Create an empty TreeSet
|
||||
static pure fn new() -> TreeSet<T> { TreeSet{map: TreeMap::new()} }
|
||||
|
||||
/// Visit all values in reverse order
|
||||
pure fn each_reverse(&self, f: fn(&T) -> bool) {
|
||||
self.map.each_key_reverse(f)
|
||||
}
|
||||
|
||||
/// Get a lazy iterator over the values in the set.
|
||||
/// Requires that it be frozen (immutable).
|
||||
pure fn iter(&self) -> TreeSetIterator/&self<T> {
|
||||
TreeSetIterator{iter: self.map.iter()}
|
||||
}
|
||||
|
||||
/// Visit the values (in-order) representing the difference
|
||||
pure fn difference(&self, other: &TreeSet<T>, f: fn(&T) -> bool) {
|
||||
|
|
@ -448,6 +432,22 @@ impl <T: Ord> TreeSet<T> {
|
|||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl <T: Ord> TreeSet<T> {
|
||||
/// Create an empty TreeSet
|
||||
static pure fn new() -> TreeSet<T> { TreeSet{map: TreeMap::new()} }
|
||||
|
||||
/// Visit all values in reverse order
|
||||
pure fn each_reverse(&self, f: fn(&T) -> bool) {
|
||||
self.map.each_key_reverse(f)
|
||||
}
|
||||
|
||||
/// Get a lazy iterator over the values in the set.
|
||||
/// Requires that it be frozen (immutable).
|
||||
pure fn iter(&self) -> TreeSetIterator/&self<T> {
|
||||
TreeSetIterator{iter: self.map.iter()}
|
||||
}
|
||||
|
||||
/// Visit the values (in-order) representing the intersection
|
||||
pure fn intersection(&self, other: &TreeSet<T>, f: fn(&T) -> bool) {
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue