standard_lib/fs/path/
iter.rs

1use std::iter::FusedIterator;
2use std::marker::PhantomData;
3use std::mem;
4
5use crate::fs::OwnedPath;
6use crate::fs::path::{Path, PathState, Rel};
7
8// TODO: OwnedComponents?
9pub struct IntoComponents<State: PathState> {
10    pub(crate) _state: PhantomData<fn() -> State>,
11    pub(crate) path: Vec<u8>,
12}
13
14impl<S: PathState> Iterator for IntoComponents<S> {
15    type Item = OwnedPath<Rel>;
16
17    fn next(&mut self) -> Option<Self::Item> {
18        if self.path.is_empty() {
19            None?
20        }
21        let mut tail = 1;
22
23        while let Some(ch) = self.path.get(tail) && *ch != b'/' {
24            tail += 1;
25        }
26
27        let remainder = self.path.split_off(tail);
28
29        Some(unsafe { OwnedPath::from_unchecked_bytes(
30            mem::replace(&mut self.path, remainder)
31        ) })
32    }
33}
34
35impl<S: PathState> FusedIterator for IntoComponents<S> {}
36
37pub struct Components<'a, State: PathState> {
38    pub(crate) _state: PhantomData<fn() -> State>,
39    pub(crate) path: &'a [u8],
40    pub(crate) head: usize,
41}
42
43impl<'a, S: PathState> Iterator for Components<'a, S> {
44    type Item = &'a Path<Rel>;
45
46    fn next(&mut self) -> Option<Self::Item> {
47        if self.head >= self.path.len() {
48            None?
49        }
50        let mut tail = self.head + 1;
51        
52        while let Some(ch) = self.path.get(tail) && *ch != b'/' {
53            tail += 1;
54        }
55
56        let res = &self.path[self.head..tail];
57        self.head = tail;
58
59        unsafe {
60            Some(Path::from_unchecked_bytes(res))
61        }
62    }
63}
64
65impl<'a, S: PathState> FusedIterator for Components<'a, S> {}
66
67pub struct Ancestors<'a, State: PathState + 'a> {
68    pub(crate) _state: PhantomData<fn() -> State>,
69    pub(crate) path: &'a [u8],
70    pub(crate) index: usize,
71}
72
73impl<'a, S: PathState> Iterator for Ancestors<'a, S> {
74    type Item = &'a Path<S>;
75
76    fn next(&mut self) -> Option<Self::Item> {
77        if self.index >= self.path.len() {
78            None?
79        }
80        self.index += 1;
81
82        while let Some(ch) = self.path.get(self.index) && *ch != b'/' {
83            self.index += 1;
84        }
85
86        unsafe {
87            Some(Path::from_unchecked_bytes(
88                &self.path[..self.index]
89            ))
90        }
91    }
92}
93
94impl<'a, S: PathState> FusedIterator for Ancestors<'a, S> {}