use std::collections::VecDeque;
use std::convert::{TryInto,TryFrom};
use std::ops::{Neg,Index,IndexMut};
use std::fmt::Debug;
use num_traits::{Zero,One,CheckedAdd,CheckedSub};
#[derive(Clone,Debug,Hash)]
pub struct Deque<T,I:Offset> {
advanced : I,
v : VecDeque<T>,
}
pub trait Offset : Clone + Debug + Neg + PartialEq + Eq {
fn try_increment(&mut self) -> Option<()>;
fn try_decrement(&mut self) -> Option<()>;
fn zero() -> Self;
fn index_input(&self, input: Self) -> Option<usize>;
fn index_output(&self, inner: usize) -> Option<Self>;
}
impl<T> Offset for T where T
: Clone + Debug + Neg + PartialEq + Eq
+ Zero
+ One
+ CheckedAdd
+ CheckedSub
+ TryInto<usize>
+ TryFrom<usize>
{
fn try_increment(&mut self) -> Option<()> {
*self = self.checked_add(&One::one())?;
Some(())
}
fn try_decrement(&mut self) -> Option<()> {
*self = self.checked_sub(&One::one())?;
Some(())
}
fn index_input(&self, input: Self) -> Option<usize> {
input.checked_sub(&self)?.try_into().ok()
}
fn index_output(&self, output: usize) -> Option<Self> {
self.checked_add(&output.try_into().ok()?)
}
fn zero() -> Self { Zero::zero() }
}
impl<T, I:Offset> Index<I> for Deque<T,I> {
type Output = T;
fn index(&self, i : I) -> &T { self.get(i).unwrap() }
}
impl<T, I:Offset> IndexMut<I> for Deque<T,I> {
fn index_mut(&mut self, i : I) -> &mut T { self.get_mut(i).unwrap() }
}
impl<T, I:Offset> Default for Deque<T,I> {
fn default() -> Self { Self::new() }
}
pub struct Iter<'v, T, I:Offset> {
i : I,
j : I,
v : &'v Deque<T,I>,
}
impl<'v, T, I:Offset> Iterator for Iter<'v,T,I> {
type Item = (I,&'v T);
fn next(&mut self) -> Option<Self::Item> {
if self.i == self.j { return None }
let i = self.i.clone();
let r = (i.clone(), self.v.get(i)?);
self.i.try_increment().unwrap();
Some(r)
}
}
impl<'v, T, I:Offset> DoubleEndedIterator for Iter<'v,T,I> {
fn next_back(&mut self) -> Option<Self::Item> {
if self.i == self.j { return None }
self.j.try_decrement().unwrap();
let j = self.j.clone();
let r = (j.clone(), self.v.get(j)?);
Some(r)
}
}
impl<'v, T, I:Offset> IntoIterator
for &'v Deque<T,I> {
type Item = (I, &'v T);
type IntoIter = Iter<'v,T,I>;
fn into_iter(self) -> Iter<'v,T,I> {
Iter {
i : self.front_index(),
j : self.end_index(),
v : self,
}
}
}
impl<T, I:Offset> Deque<T,I> {
pub fn new() -> Self { Deque {
advanced : Offset::zero(),
v : VecDeque::new(),
} }
pub fn with_capacity(cap : usize) -> Self {
Deque {
advanced : Offset::zero(),
v : VecDeque::with_capacity(cap),
}
}
pub fn len(&self) -> usize { self.v.len() }
pub fn is_empty(&self) -> bool { self.v.is_empty() }
pub fn front (& self) -> Option<& T> { self.v.front () }
pub fn back (& self) -> Option<& T> { self.v.back () }
pub fn front_mut(&mut self) -> Option<&mut T> { self.v.front_mut() }
pub fn back_mut (&mut self) -> Option<&mut T> { self.v.back_mut () }
pub fn get(&self, i : I) -> Option<&T> {
self.v.get( self.advanced.index_input(i)? )
}
pub fn get_mut(&mut self, i : I) -> Option<&mut T> {
self.v.get_mut( self.advanced.index_input(i)? )
}
pub fn push_front(&mut self, e : T) -> I {
let p = 0;
self.v.push_front(e);
self.advanced.try_decrement().unwrap();
self.advanced.index_output(p).unwrap()
}
pub fn push_back(&mut self, e : T) -> I {
let p = self.v.len();
self.v.push_back(e);
self.advanced.index_output(p).unwrap()
}
pub fn pop_front(&mut self) -> Option<T> {
let r = self.v.pop_front()?;
self.advanced.try_increment().unwrap();
Some(r)
}
pub fn pop_back(&mut self) -> Option<T> {
let r = self.v.pop_back()?;
Some(r)
}
pub fn swap_remove_front(&mut self, i: I) -> Option<T> {
let r = self.v.swap_remove_front( self.advanced.index_input(i)? )?;
self.advanced.try_increment().unwrap();
Some(r)
}
pub fn swap_remove_back(&mut self, i: I) -> Option<T> {
let r = self.v.swap_remove_back( self.advanced.index_input(i)? )?;
Some(r)
}
pub fn front_index(&self) -> I {
self.advanced.index_output(0).unwrap()
}
pub fn end_index(&self) -> I {
self.advanced.index_output(self.len()).unwrap()
}
pub fn counter(&self) -> &I { &self.advanced }
pub fn counter_mut(&mut self) -> &mut I { &mut self.advanced }
pub fn inner(&self) -> &VecDeque<T> { &self.v }
pub fn inner_mut(&mut self) -> &mut VecDeque<T> { &mut self.v }
pub fn into_parts(self) -> (I, VecDeque<T>) {
(self.advanced, self.v)
}
pub fn from_parts(advanced: I, v: VecDeque<T>) -> Self {
Self { advanced, v }
}
pub fn as_parts(&self) -> (&I, &VecDeque<T>) {
(&self.advanced, &self.v)
}
pub fn as_mut_parts(&mut self) -> (&mut I, &mut VecDeque<T>) {
(&mut self.advanced, &mut self.v)
}
}
#[cfg(test)]
impl<I:Offset> Deque<char,I> {
fn chk(&self) -> String {
let s : String = self.inner().iter().collect();
format!("{:?} {} {}", self.front_index(), self.len(), &s)
}
}
#[test]
fn with_i8() {
let mut siv : Deque<char,i8> = Default::default();
assert_eq!(None, siv.pop_front());
assert_eq!(None, siv.pop_back());
for (i, c) in ('a'..='g').enumerate() {
let j = siv.push_back(c);
assert_eq!(i, j as usize);
}
assert_eq!('d', siv[ 3]);
assert_eq!(-1, siv.push_front('Z'));
assert_eq!( 7, siv.push_back('H'));
assert_eq!("-1 9 ZabcdefgH", siv.chk());
assert_eq!('Z', siv[-1]);
assert_eq!('d', siv[ 3]);
assert_eq!(None, siv.swap_remove_front(-2));
assert_eq!(None, siv.swap_remove_back(10));
assert_eq!(Some('Z'), siv.pop_front());
assert_eq!(Some('H'), siv.pop_back());
assert_eq!("0 7 abcdefg", siv.chk());
assert_eq!(Some('c'), siv.swap_remove_front(2));
assert_eq!("1 6 badefg", siv.chk());
assert_eq!(Some('d'), siv.swap_remove_back(3));
assert_eq!("1 5 bagef", siv.chk());
*siv.get_mut(4).unwrap() = 'E';
assert_eq!("1 5 bagEf", siv.chk());
assert_eq!(6, siv.end_index());
let (a,v) = siv.into_parts();
let mut siv = Deque::from_parts(a,v);
assert_eq!("1 5 bagEf", siv.chk());
siv.inner_mut()[0] = 'B';
assert_eq!("1 5 BagEf", siv.chk());
let mut l = vec![];
for ent in &siv { l.push(ent); }
assert_eq!("[(1, 'B'), (2, 'a'), (3, 'g'), (4, 'E'), (5, 'f')]",
format!("{:?}", &l));
let mut l = vec![];
for ent in siv.into_iter().rev() { l.push(ent); }
assert_eq!("[(5, 'f'), (4, 'E'), (3, 'g'), (2, 'a'), (1, 'B')]",
format!("{:?}", &l));
}
#[test]
fn with_isize() {
let mut siv = <Deque<String,isize>>::new();
siv.push_back("s".to_owned());
}
#[test]
fn with_big() {
#[cfg(target_pointer_width="16")]
let a = 123 * 1_000_000_i32;
#[cfg(target_pointer_width="32")]
let a = 123 * 1_000_000_000_000_000_i64;
#[cfg(target_pointer_width="64")]
let a = 123 * 1_000_000_000_000_000_000_000_000_000_000_i128;
assert_eq!(None, usize::try_from(a).ok());
let v : VecDeque<char> = Default::default();
let mut siv = Deque::from_parts(a,v);
siv.push_back('a');
siv.push_back('b');
assert_eq!('a', *siv.front().unwrap());
assert_eq!('b', *siv.back ().unwrap());
*siv.front_mut().unwrap() = 'A';
*siv.back_mut() .unwrap() = 'B';
assert_eq!(format!("{} 2 AB", &a), siv.chk());
assert_eq!(None, siv.get(0));
}