into_iter() for reader
This commit is contained in:
parent
e18539a982
commit
103b677d21
124
lib/src/db.rs
124
lib/src/db.rs
@ -226,6 +226,10 @@ where
|
||||
pub fn iter(&self) -> ReaderIter<'_, T> {
|
||||
ReaderIter::new(self)
|
||||
}
|
||||
|
||||
pub fn into_iter(self) -> ReaderIntoIter<T> {
|
||||
ReaderIntoIter::new(self)
|
||||
}
|
||||
}
|
||||
|
||||
pub struct ReaderIter<'a, T>
|
||||
@ -310,6 +314,100 @@ where
|
||||
}
|
||||
}
|
||||
|
||||
pub struct ReaderIntoIter<T>
|
||||
where
|
||||
T: bincode::Decode,
|
||||
{
|
||||
reader: Reader<T>,
|
||||
index: Option<usize>,
|
||||
}
|
||||
|
||||
impl<T> ReaderIntoIter<T>
|
||||
where
|
||||
T: bincode::Decode,
|
||||
{
|
||||
fn new(reader: Reader<T>) -> Self {
|
||||
Self {
|
||||
reader,
|
||||
index: None,
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl<T> Iterator for ReaderIntoIter<T>
|
||||
where
|
||||
T: bincode::Decode,
|
||||
{
|
||||
type Item = T;
|
||||
|
||||
fn next(&mut self) -> Option<Self::Item> {
|
||||
if self.index.is_none() && !self.reader.is_empty() {
|
||||
self.index = Some(0);
|
||||
}
|
||||
|
||||
match self.index {
|
||||
Some(i) if i < self.reader.len() => self.nth(i),
|
||||
_ => None,
|
||||
}
|
||||
}
|
||||
|
||||
fn nth(&mut self, n: usize) -> Option<Self::Item> {
|
||||
if self.reader.len() <= n {
|
||||
return None;
|
||||
}
|
||||
self.index = Some(n + 1);
|
||||
|
||||
let item = self.reader.get(n);
|
||||
match item {
|
||||
Ok(item) => Some(item),
|
||||
Err(_) => None,
|
||||
}
|
||||
}
|
||||
|
||||
fn size_hint(&self) -> (usize, Option<usize>) {
|
||||
let len = self.reader.len();
|
||||
if self.index.is_none() {
|
||||
return (len, Some(len));
|
||||
}
|
||||
|
||||
let index = self.index.unwrap();
|
||||
let rem = if len > index + 1 {
|
||||
len - (index + 1)
|
||||
} else {
|
||||
0
|
||||
};
|
||||
(rem, Some(rem))
|
||||
}
|
||||
|
||||
fn count(self) -> usize
|
||||
where
|
||||
Self: Sized,
|
||||
{
|
||||
self.reader.len()
|
||||
}
|
||||
}
|
||||
|
||||
impl<T> ExactSizeIterator for ReaderIntoIter<T>
|
||||
where
|
||||
T: bincode::Decode,
|
||||
{
|
||||
fn len(&self) -> usize {
|
||||
self.reader.len()
|
||||
}
|
||||
}
|
||||
|
||||
impl<T> IntoIterator for Reader<T>
|
||||
where
|
||||
T: bincode::Decode,
|
||||
{
|
||||
type Item = T;
|
||||
type IntoIter = ReaderIntoIter<Self::Item>;
|
||||
|
||||
fn into_iter(self) -> Self::IntoIter {
|
||||
self.into_iter()
|
||||
}
|
||||
}
|
||||
|
||||
#[cfg(test)]
|
||||
mod test {
|
||||
use super::*;
|
||||
@ -380,4 +478,30 @@ mod test {
|
||||
assert_eq!(pair.0, pair.1);
|
||||
});
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn test_write_read_into_iter() {
|
||||
let dir = tempdir().expect("tempdir");
|
||||
let tmpfile = dir.path().join("test.tmp");
|
||||
let opts = WriterOpts {
|
||||
compress_lvl: 1,
|
||||
data_buf_size: 10 * 1024 * 1024,
|
||||
out_buf_size: 10 * 1024 * 1024,
|
||||
current_buf_size: 4096,
|
||||
};
|
||||
let mut writer: Writer<TestData> = Writer::new(&tmpfile, opts).expect("new writer");
|
||||
|
||||
let items_iter = gen_data(10);
|
||||
let items: Vec<TestData> = items_iter.collect();
|
||||
|
||||
writer.load(&mut items.clone().into_iter()).expect("load");
|
||||
writer.finish().expect("finish write");
|
||||
|
||||
let reader: Reader<TestData> = Reader::new(&tmpfile, 2048).expect("new reader");
|
||||
assert_eq!(items.len(), reader.len());
|
||||
|
||||
items.into_iter().zip(reader).for_each(|pair| {
|
||||
assert_eq!(pair.0, pair.1);
|
||||
});
|
||||
}
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user