mod cursor;
mod iter;
mod list;
mod map;
mod node;
pub use cursor::*;
pub use iter::*;
pub use list::*;
pub use map::*;
pub use node::*;
pub type KeyValueList<K, V> = KeyNodeList<K, ValueNode<K, V>>;
macro_rules! node_prev_mut {
($list:expr, $key:expr) => {
$list
.node_mut::<K>($key)
.unwrap()
.prev_mut::<$crate::node::Token>()
};
($node:expr) => {
$node.prev_mut::<$crate::node::Token>()
};
}
pub(crate) use node_prev_mut;
macro_rules! node_next_mut {
($list:expr, $key:expr) => {
$list
.node_mut::<K>($key)
.unwrap()
.next_mut::<$crate::node::Token>()
};
($node:expr) => {
$node.next_mut::<$crate::node::Token>()
};
}
pub(crate) use node_next_mut;
#[cfg(test)]
mod test {
use super::*;
#[test]
fn test_capacity() {
let mut list = KeyValueList::new();
assert_eq!(list.front_key(), None);
assert_eq!(list.back_key(), None);
assert_eq!(list.len(), 0);
assert!(list.is_empty());
list.push_back(1, 1).unwrap();
assert_eq!(list.front_key(), Some(&1));
assert_eq!(list.back_key(), Some(&1));
assert_eq!(list.len(), 1);
assert!(!list.is_empty());
list.push_back(2, 2).unwrap();
assert_eq!(list.front_key(), Some(&1));
assert_eq!(list.back_key(), Some(&2));
assert_eq!(list.len(), 2);
assert!(!list.is_empty());
list.clear();
assert_eq!(list.front_key(), None);
assert_eq!(list.back_key(), None);
assert_eq!(list.len(), 0);
assert!(list.is_empty());
}
#[test]
fn test_push_into_iter() {
let mut list = KeyValueList::new();
for i in 0..10 {
list.push_back(i, i).unwrap();
}
let vec = list.into_iter().collect::<Vec<_>>();
assert_eq!(vec.len(), 10);
for (i, (k, n)) in vec.into_iter().enumerate() {
assert_eq!(i as i32, k);
assert_eq!(i as i32, n.into_value());
}
}
#[test]
fn test_push_pop() {
let mut list = KeyValueList::new();
assert_eq!(list.pop_back(), None);
assert_eq!(list.pop_front(), None);
for i in 0..10 {
list.push_back(i, i).unwrap();
}
let mut cur = 9;
while let Some((k, n)) = list.pop_back() {
assert_eq!(cur, k);
assert_eq!(cur, n.into_value());
cur -= 1;
}
assert_eq!(cur, -1);
}
#[test]
fn test_push_front_iter() {
let mut list = KeyValueList::new();
for i in 0..10 {
list.push_front(i, i * 2).unwrap();
}
for (i, (k, n)) in list.iter().enumerate() {
assert_eq!(9 - i, *k);
assert_eq!((9 - i) * 2, *n.value());
}
for (i, k) in list.keys().enumerate() {
assert_eq!(9 - i, *k);
}
for (i, n) in list.nodes().enumerate() {
assert_eq!((9 - i) * 2, *n.value());
}
}
#[test]
fn test_cursor_move() {
let mut list = KeyValueList::new();
for i in 0..10 {
list.push_front(i, i * 2).unwrap();
}
let mut cur = list.cursor_back();
assert_eq!(cur.key(), Some(&0));
cur.move_prev();
assert_eq!(cur.key(), Some(&1));
dbg!(cur.key());
dbg!(cur.node());
assert_eq!(cur.next_key(), Some(&0));
cur.move_next();
assert_eq!(cur.key(), Some(&0));
cur.move_next();
assert_eq!(cur.key(), None);
cur.move_next();
assert_eq!(cur.key(), Some(&9));
}
#[test]
fn test_cursor_insert_remove() {
let mut list = KeyValueList::new();
for i in 0..10 {
list.push_back(i * 10, i * 10).unwrap();
}
let mut cur = list.cursor_front_mut();
while cur.key() != Some(&40) {
cur.move_next();
}
cur.insert_before(37, 37).unwrap();
cur.insert_before(38, 38).unwrap();
cur.insert_before(39, 39).unwrap();
cur.insert_after(42, 42).unwrap();
cur.insert_after(41, 41).unwrap();
for i in 0..3 {
assert_eq!(
cur.remove_current().map(|(k, n)| (k, n.into_value())),
Some((40 + i, 40 + i))
);
}
assert_eq!(cur.key(), Some(&50));
for i in 0..3 {
cur.move_prev();
assert_eq!(
cur.remove_current().map(|(k, n)| (k, n.into_value())),
Some((39 - i, 39 - i))
);
}
assert_eq!(cur.prev_key(), Some(&30));
}
#[test]
fn test_from_eq() {
let list1 = KeyValueList::from([(1, 1), (2, 2), (3, 3)]);
let list2 = KeyValueList::from([(1, 1), (2, 2), (3, 3)]);
let list3 = KeyValueList::from([(1, 1), (2, 2), (3, 4)]);
let list4: KeyValueList<i32, i32> = [(1, 1), (2, 2), (3, 4)].into_iter().collect();
let list5: KeyValueList<i32, ()> = [1, 2, 3].into_iter().collect();
let mut list6: KeyValueList<i32, ()> = KeyValueList::new();
list6.extend([1, 2, 3]);
assert_eq!(list1, list2);
assert_ne!(list1, list3);
assert_eq!(list3, list4);
assert_eq!(list5, list6);
}
}