orx_concurrent_iter/chain/
con_iter_known_len_i.rs1use crate::{
2 ConcurrentIter, ExactSizeConcurrentIter,
3 chain::chunk_puller_known_len_i::ChainedChunkPullerKnownLenI,
4};
5
6pub struct ChainKnownLenI<I, J>
9where
10 I: ConcurrentIter,
11 J: ConcurrentIter<Item = I::Item>,
12{
13 i: I,
14 j: J,
15 len_i: usize,
16}
17
18impl<I, J> ChainKnownLenI<I, J>
19where
20 I: ConcurrentIter,
21 J: ConcurrentIter<Item = I::Item>,
22{
23 pub(crate) fn new(i: I, j: J, len_i: usize) -> Self {
24 Self { i, j, len_i }
25 }
26}
27
28impl<I, J> ConcurrentIter for ChainKnownLenI<I, J>
29where
30 I: ConcurrentIter,
31 J: ConcurrentIter<Item = I::Item>,
32{
33 type Item = I::Item;
34
35 type SequentialIter = core::iter::Chain<I::SequentialIter, J::SequentialIter>;
36
37 type ChunkPuller<'i>
38 = ChainedChunkPullerKnownLenI<'i, I, J>
39 where
40 Self: 'i;
41
42 fn into_seq_iter(self) -> Self::SequentialIter {
43 self.i.into_seq_iter().chain(self.j.into_seq_iter())
44 }
45
46 fn skip_to_end(&self) {
47 self.i.skip_to_end();
48 self.j.skip_to_end();
49 }
50
51 fn next(&self) -> Option<Self::Item> {
52 self.i.next().or_else(|| self.j.next())
53 }
54
55 fn next_with_idx(&self) -> Option<(usize, Self::Item)> {
56 self.i
57 .next_with_idx()
58 .or_else(|| self.j.next_with_idx().map(|(idx, x)| (self.len_i + idx, x)))
59 }
60
61 fn size_hint(&self) -> (usize, Option<usize>) {
62 let (l1, u1) = self.i.size_hint();
63 let (l2, u2) = self.j.size_hint();
64 match (u1, u2) {
65 (Some(u1), Some(u2)) => (l1 + l2, Some(u1 + u2)),
66 _ => (l1 + l2, None),
67 }
68 }
69
70 fn is_completed_when_none_returned(&self) -> bool {
71 true
72 }
73
74 fn chunk_puller(&self, chunk_size: usize) -> Self::ChunkPuller<'_> {
75 ChainedChunkPullerKnownLenI::new(&self.i, &self.j, chunk_size, self.len_i)
76 }
77}
78
79impl<I, J> ExactSizeConcurrentIter for ChainKnownLenI<I, J>
80where
81 I: ExactSizeConcurrentIter,
82 J: ExactSizeConcurrentIter<Item = I::Item>,
83{
84 fn len(&self) -> usize {
85 self.i.len() + self.j.len()
86 }
87}