Adding in to_stream
This commit is contained in:
parent
e34fc50ad0
commit
9e72a02441
|
@ -1,4 +1,4 @@
|
|||
use futures::Async;
|
||||
use futures::{Stream, Poll, Async};
|
||||
//use std::iter::Iterator;
|
||||
|
||||
|
||||
|
@ -107,7 +107,14 @@ pub trait SignalList {
|
|||
}
|
||||
|
||||
#[inline]
|
||||
fn as_mut(&mut self) -> &mut Self {
|
||||
fn to_stream(self) -> SignalListStream<Self> where Self: Sized {
|
||||
SignalListStream {
|
||||
signal: self,
|
||||
}
|
||||
}
|
||||
|
||||
#[inline]
|
||||
fn by_ref(&mut self) -> &mut Self {
|
||||
self
|
||||
}
|
||||
}
|
||||
|
@ -131,6 +138,24 @@ impl<A, B, F> SignalList for Map<A, F>
|
|||
}
|
||||
|
||||
|
||||
pub struct SignalListStream<A> {
|
||||
signal: A,
|
||||
}
|
||||
|
||||
impl<A: SignalList> Stream for SignalListStream<A> {
|
||||
type Item = ListChange<A::Item>;
|
||||
type Error = ();
|
||||
|
||||
#[inline]
|
||||
fn poll(&mut self) -> Poll<Option<Self::Item>, Self::Error> {
|
||||
match self.signal.poll() {
|
||||
Async::Ready(some) => Ok(Async::Ready(some)),
|
||||
Async::NotReady => Ok(Async::NotReady),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
pub struct FilterMap<A, B> {
|
||||
length: usize,
|
||||
indexes: Vec<Option<usize>>,
|
||||
|
@ -278,15 +303,16 @@ impl<A, B, F> SignalList for FilterMap<A, F>
|
|||
|
||||
#[cfg(test)]
|
||||
mod tests {
|
||||
use futures::{Future, Poll, task};
|
||||
use super::*;
|
||||
|
||||
struct Tester<A> {
|
||||
changes: Vec<ListChange<A>>,
|
||||
changes: Vec<Async<ListChange<A>>>,
|
||||
}
|
||||
|
||||
impl<A> Tester<A> {
|
||||
#[inline]
|
||||
fn new(changes: Vec<ListChange<A>>) -> Self {
|
||||
fn new(changes: Vec<Async<ListChange<A>>>) -> Self {
|
||||
Self { changes }
|
||||
}
|
||||
}
|
||||
|
@ -297,7 +323,13 @@ mod tests {
|
|||
#[inline]
|
||||
fn poll(&mut self) -> Async<Option<ListChange<Self::Item>>> {
|
||||
if self.changes.len() > 0 {
|
||||
Async::Ready(Some(self.changes.remove(0)))
|
||||
match self.changes.remove(0) {
|
||||
Async::NotReady => {
|
||||
task::current().notify();
|
||||
Async::NotReady
|
||||
},
|
||||
Async::Ready(change) => Async::Ready(Some(change)),
|
||||
}
|
||||
|
||||
} else {
|
||||
Async::Ready(None)
|
||||
|
@ -306,19 +338,94 @@ mod tests {
|
|||
}
|
||||
|
||||
|
||||
struct TesterFuture<A, B> {
|
||||
signal_list: A,
|
||||
callback: B,
|
||||
}
|
||||
|
||||
impl<A: SignalList, B: FnMut(&mut A, ListChange<A::Item>)> TesterFuture<A, B> {
|
||||
#[inline]
|
||||
fn new(signal_list: A, callback: B) -> Self {
|
||||
Self { signal_list, callback }
|
||||
}
|
||||
}
|
||||
|
||||
impl<A, B> Future for TesterFuture<A, B>
|
||||
where A: SignalList,
|
||||
B: FnMut(&mut A, ListChange<A::Item>) {
|
||||
|
||||
type Item = ();
|
||||
type Error = ();
|
||||
|
||||
#[inline]
|
||||
fn poll(&mut self) -> Poll<Self::Item, Self::Error> {
|
||||
loop {
|
||||
return match self.signal_list.poll() {
|
||||
Async::Ready(Some(change)) => {
|
||||
(self.callback)(&mut self.signal_list, change);
|
||||
continue;
|
||||
},
|
||||
Async::Ready(None) => Ok(Async::Ready(())),
|
||||
Async::NotReady => Ok(Async::NotReady),
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fn run<A: SignalList, B: FnMut(&mut A, ListChange<A::Item>) -> C, C>(signal_list: A, mut callback: B) -> Vec<C> {
|
||||
let mut changes = vec![];
|
||||
|
||||
TesterFuture::new(signal_list, |signal, change| {
|
||||
changes.push(callback(signal, change));
|
||||
}).wait().unwrap();
|
||||
|
||||
changes
|
||||
}
|
||||
|
||||
|
||||
#[test]
|
||||
fn filter_map_insert_at() {
|
||||
fn filter_map() {
|
||||
#[derive(Debug, PartialEq, Eq)]
|
||||
struct Change {
|
||||
length: usize,
|
||||
indexes: Vec<Option<usize>>,
|
||||
change: ListChange<u32>,
|
||||
}
|
||||
|
||||
let input = Tester::new(vec![
|
||||
ListChange::Replace { values: vec![0, 1, 2, 3, 4, 5] },
|
||||
ListChange::InsertAt { index: 0, value: 6 },
|
||||
ListChange::InsertAt { index: 2, value: 7 },
|
||||
ListChange::InsertAt { index: 5, value: 8 },
|
||||
ListChange::InsertAt { index: 7, value: 9 },
|
||||
ListChange::InsertAt { index: 9, value: 10 },
|
||||
ListChange::InsertAt { index: 11, value: 11 },
|
||||
Async::Ready(ListChange::Replace { values: vec![0, 1, 2, 3, 4, 5] }),
|
||||
Async::NotReady,
|
||||
Async::Ready(ListChange::InsertAt { index: 0, value: 6 }),
|
||||
Async::Ready(ListChange::InsertAt { index: 2, value: 7 }),
|
||||
Async::NotReady,
|
||||
Async::NotReady,
|
||||
Async::NotReady,
|
||||
Async::Ready(ListChange::InsertAt { index: 5, value: 8 }),
|
||||
Async::Ready(ListChange::InsertAt { index: 7, value: 9 }),
|
||||
Async::Ready(ListChange::InsertAt { index: 9, value: 10 }),
|
||||
Async::NotReady,
|
||||
Async::Ready(ListChange::InsertAt { index: 11, value: 11 }),
|
||||
Async::NotReady,
|
||||
Async::Ready(ListChange::InsertAt { index: 0, value: 0 }),
|
||||
Async::NotReady,
|
||||
Async::NotReady,
|
||||
Async::Ready(ListChange::InsertAt { index: 1, value: 0 }),
|
||||
Async::Ready(ListChange::InsertAt { index: 5, value: 0 }),
|
||||
Async::NotReady,
|
||||
Async::Ready(ListChange::InsertAt { index: 5, value: 12 }),
|
||||
Async::NotReady,
|
||||
Async::Ready(ListChange::RemoveAt { index: 0 }),
|
||||
Async::Ready(ListChange::RemoveAt { index: 0 }),
|
||||
Async::NotReady,
|
||||
Async::Ready(ListChange::RemoveAt { index: 0 }),
|
||||
Async::Ready(ListChange::RemoveAt { index: 1 }),
|
||||
Async::NotReady,
|
||||
Async::Ready(ListChange::RemoveAt { index: 0 }),
|
||||
Async::NotReady,
|
||||
Async::Ready(ListChange::RemoveAt { index: 0 }),
|
||||
]);
|
||||
|
||||
let mut output = input.filter_map(|x| {
|
||||
let output = input.filter_map(|x| {
|
||||
if x == 3 || x == 4 || x > 5 {
|
||||
Some(x + 100)
|
||||
} else {
|
||||
|
@ -329,34 +436,26 @@ mod tests {
|
|||
assert_eq!(output.length, 0);
|
||||
assert_eq!(output.indexes, vec![]);
|
||||
|
||||
assert_eq!(output.poll(), Async::Ready(Some(ListChange::Replace {
|
||||
values: vec![103, 104],
|
||||
})));
|
||||
assert_eq!(output.length, 2);
|
||||
assert_eq!(output.indexes, vec![None, None, None, Some(0), Some(1), None]);
|
||||
let changes = run(output, |output, change| {
|
||||
Change {
|
||||
change: change,
|
||||
length: output.length,
|
||||
indexes: output.indexes.clone(),
|
||||
}
|
||||
});
|
||||
|
||||
assert_eq!(output.poll(), Async::Ready(Some(ListChange::InsertAt { index: 0, value: 106 })));
|
||||
assert_eq!(output.length, 3);
|
||||
assert_eq!(output.indexes, vec![Some(0), None, None, None, Some(1), Some(2), None]);
|
||||
|
||||
assert_eq!(output.poll(), Async::Ready(Some(ListChange::InsertAt { index: 1, value: 107 })));
|
||||
assert_eq!(output.length, 4);
|
||||
assert_eq!(output.indexes, vec![Some(0), None, Some(1), None, None, Some(2), Some(3), None]);
|
||||
|
||||
assert_eq!(output.poll(), Async::Ready(Some(ListChange::InsertAt { index: 2, value: 108 })));
|
||||
assert_eq!(output.length, 5);
|
||||
assert_eq!(output.indexes, vec![Some(0), None, Some(1), None, None, Some(2), Some(3), Some(4), None]);
|
||||
|
||||
assert_eq!(output.poll(), Async::Ready(Some(ListChange::InsertAt { index: 4, value: 109 })));
|
||||
assert_eq!(output.length, 6);
|
||||
assert_eq!(output.indexes, vec![Some(0), None, Some(1), None, None, Some(2), Some(3), Some(4), Some(5), None]);
|
||||
|
||||
assert_eq!(output.poll(), Async::Ready(Some(ListChange::InsertAt { index: 6, value: 110 })));
|
||||
assert_eq!(output.length, 7);
|
||||
assert_eq!(output.indexes, vec![Some(0), None, Some(1), None, None, Some(2), Some(3), Some(4), Some(5), Some(6), None]);
|
||||
|
||||
assert_eq!(output.poll(), Async::Ready(Some(ListChange::InsertAt { index: 7, value: 111 })));
|
||||
assert_eq!(output.length, 8);
|
||||
assert_eq!(output.indexes, vec![Some(0), None, Some(1), None, None, Some(2), Some(3), Some(4), Some(5), Some(6), None, Some(7)]);
|
||||
assert_eq!(changes, vec![
|
||||
Change { length: 2, indexes: vec![None, None, None, Some(0), Some(1), None], change: ListChange::Replace { values: vec![103, 104] } },
|
||||
Change { length: 3, indexes: vec![Some(0), None, None, None, Some(1), Some(2), None], change: ListChange::InsertAt { index: 0, value: 106 } },
|
||||
Change { length: 4, indexes: vec![Some(0), None, Some(1), None, None, Some(2), Some(3), None], change: ListChange::InsertAt { index: 1, value: 107 } },
|
||||
Change { length: 5, indexes: vec![Some(0), None, Some(1), None, None, Some(2), Some(3), Some(4), None], change: ListChange::InsertAt { index: 2, value: 108 } },
|
||||
Change { length: 6, indexes: vec![Some(0), None, Some(1), None, None, Some(2), Some(3), Some(4), Some(5), None], change: ListChange::InsertAt { index: 4, value: 109 } },
|
||||
Change { length: 7, indexes: vec![Some(0), None, Some(1), None, None, Some(2), Some(3), Some(4), Some(5), Some(6), None], change: ListChange::InsertAt { index: 6, value: 110 } },
|
||||
Change { length: 8, indexes: vec![Some(0), None, Some(1), None, None, Some(2), Some(3), Some(4), Some(5), Some(6), None, Some(7)], change: ListChange::InsertAt { index: 7, value: 111 } },
|
||||
Change { length: 9, indexes: vec![None, None, Some(0), None, Some(1), Some(2), None, None, None, Some(3), Some(4), Some(5), Some(6), Some(7), None, Some(8)], change: ListChange::InsertAt { index: 2, value: 112 } },
|
||||
Change { length: 8, indexes: vec![None, Some(0), Some(1), None, None, None, Some(2), Some(3), Some(4), Some(5), Some(6), None, Some(7)], change: ListChange::RemoveAt { index: 0 } },
|
||||
Change { length: 7, indexes: vec![None, Some(0), None, None, None, Some(1), Some(2), Some(3), Some(4), Some(5), None, Some(6)], change: ListChange::RemoveAt { index: 0 } },
|
||||
Change { length: 6, indexes: vec![None, None, None, Some(0), Some(1), Some(2), Some(3), Some(4), None, Some(5)], change: ListChange::RemoveAt { index: 0 } },
|
||||
]);
|
||||
}
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue