Skip to content

Commit 74db699

Browse files
committed
auto merge of #15968 : nham/rust/keys_values_other_maps, r=alexcrichton
Adds methods for obtaining iterators over the keys or values of a SmallIntMap/TreeMap/TrieMap. Closes #14376
2 parents d30776e + 74b1aed commit 74db699

File tree

3 files changed

+131
-0
lines changed

3 files changed

+131
-0
lines changed

src/libcollections/smallintmap.rs

Lines changed: 47 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -17,6 +17,7 @@ use core::prelude::*;
1717

1818
use core::default::Default;
1919
use core::fmt;
20+
use core::iter;
2021
use core::iter::{Enumerate, FilterMap};
2122
use core::mem::replace;
2223

@@ -194,6 +195,18 @@ impl<V> SmallIntMap<V> {
194195
self.find(key).expect("key not present")
195196
}
196197

198+
/// An iterator visiting all keys in ascending order by the keys.
199+
/// Iterator element type is `uint`.
200+
pub fn keys<'r>(&'r self) -> Keys<'r, V> {
201+
self.iter().map(|(k, _v)| k)
202+
}
203+
204+
/// An iterator visiting all values in ascending order by the keys.
205+
/// Iterator element type is `&'r V`.
206+
pub fn values<'r>(&'r self) -> Values<'r, V> {
207+
self.iter().map(|(_k, v)| v)
208+
}
209+
197210
/// An iterator visiting all key-value pairs in ascending order by the keys.
198211
/// Iterator element type is `(uint, &'r V)`.
199212
///
@@ -422,6 +435,14 @@ pub struct MutEntries<'a, T> {
422435
iterator!(impl MutEntries -> (uint, &'a mut T), get_mut_ref)
423436
double_ended_iterator!(impl MutEntries -> (uint, &'a mut T), get_mut_ref)
424437

438+
/// Forward iterator over the keys of a map
439+
pub type Keys<'a, T> =
440+
iter::Map<'static, (uint, &'a T), uint, Entries<'a, T>>;
441+
442+
/// Forward iterator over the values of a map
443+
pub type Values<'a, T> =
444+
iter::Map<'static, (uint, &'a T), &'a T, Entries<'a, T>>;
445+
425446
#[cfg(test)]
426447
mod test_map {
427448
use std::prelude::*;
@@ -517,6 +538,32 @@ mod test_map {
517538
assert_eq!(m.pop(&1), None);
518539
}
519540

541+
#[test]
542+
fn test_keys() {
543+
let mut map = SmallIntMap::new();
544+
map.insert(1, 'a');
545+
map.insert(2, 'b');
546+
map.insert(3, 'c');
547+
let keys = map.keys().collect::<Vec<uint>>();
548+
assert_eq!(keys.len(), 3);
549+
assert!(keys.contains(&1));
550+
assert!(keys.contains(&2));
551+
assert!(keys.contains(&3));
552+
}
553+
554+
#[test]
555+
fn test_values() {
556+
let mut map = SmallIntMap::new();
557+
map.insert(1, 'a');
558+
map.insert(2, 'b');
559+
map.insert(3, 'c');
560+
let values = map.values().map(|&v| v).collect::<Vec<char>>();
561+
assert_eq!(values.len(), 3);
562+
assert!(values.contains(&'a'));
563+
assert!(values.contains(&'b'));
564+
assert!(values.contains(&'c'));
565+
}
566+
520567
#[test]
521568
fn test_iterator() {
522569
let mut m = SmallIntMap::new();

src/libcollections/treemap.rs

Lines changed: 41 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -141,6 +141,16 @@ impl<K: Ord, V> TreeMap<K, V> {
141141
/// Create an empty TreeMap
142142
pub fn new() -> TreeMap<K, V> { TreeMap{root: None, length: 0} }
143143

144+
/// Get a lazy iterator over the keys in the map.
145+
pub fn keys<'a>(&'a self) -> Keys<'a, K, V> {
146+
self.iter().map(|(k, _v)| k)
147+
}
148+
149+
/// Get a lazy iterator over the values in the map.
150+
pub fn values<'a>(&'a self) -> Values<'a, K, V> {
151+
self.iter().map(|(_k, v)| v)
152+
}
153+
144154
/// Get a lazy iterator over the key-value pairs in the map.
145155
/// Requires that it be frozen (immutable).
146156
pub fn iter<'a>(&'a self) -> Entries<'a, K, V> {
@@ -381,6 +391,15 @@ pub struct RevMutEntries<'a, K, V> {
381391
}
382392

383393

394+
/// TreeMap keys iterator
395+
pub type Keys<'a, K, V> =
396+
iter::Map<'static, (&'a K, &'a V), &'a K, Entries<'a, K, V>>;
397+
398+
/// TreeMap values iterator
399+
pub type Values<'a, K, V> =
400+
iter::Map<'static, (&'a K, &'a V), &'a V, Entries<'a, K, V>>;
401+
402+
384403
// FIXME #5846 we want to be able to choose between &x and &mut x
385404
// (with many different `x`) below, so we need to optionally pass mut
386405
// as a tt, but the only thing we can do with a `tt` is pass them to
@@ -1470,6 +1489,28 @@ mod test_treemap {
14701489
assert!(m_upper.iter().all(|(_, &x)| x == 0));
14711490
}
14721491

1492+
#[test]
1493+
fn test_keys() {
1494+
let vec = vec![(1i, 'a'), (2i, 'b'), (3i, 'c')];
1495+
let map = vec.move_iter().collect::<TreeMap<int, char>>();
1496+
let keys = map.keys().map(|&k| k).collect::<Vec<int>>();
1497+
assert_eq!(keys.len(), 3);
1498+
assert!(keys.contains(&1));
1499+
assert!(keys.contains(&2));
1500+
assert!(keys.contains(&3));
1501+
}
1502+
1503+
#[test]
1504+
fn test_values() {
1505+
let vec = vec![(1i, 'a'), (2i, 'b'), (3i, 'c')];
1506+
let map = vec.move_iter().collect::<TreeMap<int, char>>();
1507+
let values = map.values().map(|&v| v).collect::<Vec<char>>();
1508+
assert_eq!(values.len(), 3);
1509+
assert!(values.contains(&'a'));
1510+
assert!(values.contains(&'b'));
1511+
assert!(values.contains(&'c'));
1512+
}
1513+
14731514
#[test]
14741515
fn test_eq() {
14751516
let mut a = TreeMap::new();

src/libcollections/trie.rs

Lines changed: 43 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -18,6 +18,7 @@ use core::default::Default;
1818
use core::mem::zeroed;
1919
use core::mem;
2020
use core::uint;
21+
use core::iter;
2122
use std::hash::{Writer, Hash};
2223

2324
use {Collection, Mutable, Map, MutableMap, Set, MutableSet};
@@ -196,6 +197,18 @@ impl<T> TrieMap<T> {
196197
self.root.each_reverse(f)
197198
}
198199

200+
/// Get an iterator visiting all keys in ascending order by the keys.
201+
/// Iterator element type is `uint`.
202+
pub fn keys<'r>(&'r self) -> Keys<'r, T> {
203+
self.iter().map(|(k, _v)| k)
204+
}
205+
206+
/// Get an iterator visiting all values in ascending order by the keys.
207+
/// Iterator element type is `&'r T`.
208+
pub fn values<'r>(&'r self) -> Values<'r, T> {
209+
self.iter().map(|(_k, v)| v)
210+
}
211+
199212
/// Get an iterator over the key-value pairs in the map, ordered by keys.
200213
///
201214
/// # Example
@@ -783,6 +796,14 @@ pub struct MutEntries<'a, T> {
783796
remaining_max: uint
784797
}
785798

799+
/// Forward iterator over the keys of a map
800+
pub type Keys<'a, T> =
801+
iter::Map<'static, (uint, &'a T), uint, Entries<'a, T>>;
802+
803+
/// Forward iterator over the values of a map
804+
pub type Values<'a, T> =
805+
iter::Map<'static, (uint, &'a T), &'a T, Entries<'a, T>>;
806+
786807
// FIXME #5846: see `addr!` above.
787808
macro_rules! item { ($i:item) => {$i}}
788809

@@ -1070,6 +1091,28 @@ mod test_map {
10701091
}
10711092
}
10721093

1094+
#[test]
1095+
fn test_keys() {
1096+
let vec = vec![(1, 'a'), (2, 'b'), (3, 'c')];
1097+
let map = vec.move_iter().collect::<TrieMap<char>>();
1098+
let keys = map.keys().collect::<Vec<uint>>();
1099+
assert_eq!(keys.len(), 3);
1100+
assert!(keys.contains(&1));
1101+
assert!(keys.contains(&2));
1102+
assert!(keys.contains(&3));
1103+
}
1104+
1105+
#[test]
1106+
fn test_values() {
1107+
let vec = vec![(1, 'a'), (2, 'b'), (3, 'c')];
1108+
let map = vec.move_iter().collect::<TrieMap<char>>();
1109+
let values = map.values().map(|&v| v).collect::<Vec<char>>();
1110+
assert_eq!(values.len(), 3);
1111+
assert!(values.contains(&'a'));
1112+
assert!(values.contains(&'b'));
1113+
assert!(values.contains(&'c'));
1114+
}
1115+
10731116
#[test]
10741117
fn test_iteration() {
10751118
let empty_map : TrieMap<uint> = TrieMap::new();

0 commit comments

Comments
 (0)