]> git.lizzy.rs Git - rust.git/blob - src/librustc_data_structures/vec_linked_list.rs
Merge remote-tracking branch 'upstream/master'
[rust.git] / src / librustc_data_structures / vec_linked_list.rs
1 use crate::indexed_vec::{Idx, IndexVec};
2
3 pub fn iter<Ls>(
4     first: Option<Ls::LinkIndex>,
5     links: &'a Ls,
6 ) -> impl Iterator<Item = Ls::LinkIndex> + 'a
7 where
8     Ls: Links,
9 {
10     VecLinkedListIterator {
11         links: links,
12         current: first,
13     }
14 }
15
16 pub struct VecLinkedListIterator<Ls>
17 where
18     Ls: Links,
19 {
20     links: Ls,
21     current: Option<Ls::LinkIndex>,
22 }
23
24 impl<Ls> Iterator for VecLinkedListIterator<Ls>
25 where
26     Ls: Links,
27 {
28     type Item = Ls::LinkIndex;
29
30     fn next(&mut self) -> Option<Ls::LinkIndex> {
31         if let Some(c) = self.current {
32             self.current = <Ls as Links>::next(&self.links, c);
33             Some(c)
34         } else {
35             None
36         }
37     }
38 }
39
40 pub trait Links {
41     type LinkIndex: Copy;
42
43     fn next(links: &Self, index: Self::LinkIndex) -> Option<Self::LinkIndex>;
44 }
45
46 impl<Ls> Links for &Ls
47 where
48     Ls: Links,
49 {
50     type LinkIndex = Ls::LinkIndex;
51
52     fn next(links: &Self, index: Ls::LinkIndex) -> Option<Ls::LinkIndex> {
53         <Ls as Links>::next(links, index)
54     }
55 }
56
57 pub trait LinkElem {
58     type LinkIndex: Copy;
59
60     fn next(elem: &Self) -> Option<Self::LinkIndex>;
61 }
62
63 impl<L, E> Links for IndexVec<L, E>
64 where
65     E: LinkElem<LinkIndex = L>,
66     L: Idx,
67 {
68     type LinkIndex = L;
69
70     fn next(links: &Self, index: L) -> Option<L> {
71         <E as LinkElem>::next(&links[index])
72     }
73 }