diff options
Diffstat (limited to 'minirust.rs')
-rw-r--r-- | minirust.rs | 68 |
1 files changed, 68 insertions, 0 deletions
diff --git a/minirust.rs b/minirust.rs new file mode 100644 index 000000000..d92c03bea --- /dev/null +++ b/minirust.rs | |||
@@ -0,0 +1,68 @@ | |||
1 | pub struct NodeKind(u16); | ||
2 | |||
3 | pub struct File { | ||
4 | text: String, | ||
5 | nodes: Vec<NodeData>, | ||
6 | } | ||
7 | |||
8 | struct NodeData { | ||
9 | kind: NodeKind, | ||
10 | range: (u32, u32), | ||
11 | parent: Option<u32>, | ||
12 | first_child: Option<u32>, | ||
13 | next_sibling: Option<u32>, | ||
14 | } | ||
15 | |||
16 | #[derive(Clone, Copy)] | ||
17 | pub struct Node<'f> { | ||
18 | file: &'f File, | ||
19 | idx: u32, | ||
20 | } | ||
21 | |||
22 | pub struct Children<'f> { | ||
23 | next: Option<Node<'f>>, | ||
24 | } | ||
25 | |||
26 | impl File { | ||
27 | pub fn root<'f>(&'f self) -> Node<'f> { | ||
28 | assert!(!self.nodes.is_empty()); | ||
29 | Node { file: self, idx: 0 } | ||
30 | } | ||
31 | } | ||
32 | |||
33 | impl<'f> Node<'f> { | ||
34 | pub fn kind(&self) -> NodeKind { | ||
35 | self.data().kind | ||
36 | } | ||
37 | |||
38 | pub fn text(&self) -> &'f str { | ||
39 | let (start, end) = self.data().range; | ||
40 | &self.file.text[start as usize..end as usize] | ||
41 | } | ||
42 | |||
43 | pub fn parent(&self) -> Option<Node<'f>> { | ||
44 | self.as_node(self.data().parent) | ||
45 | } | ||
46 | |||
47 | pub fn children(&self) -> Children<'f> { | ||
48 | Children { next: self.as_node(self.data().first_child) } | ||
49 | } | ||
50 | |||
51 | fn data(&self) -> &'f NodeData { | ||
52 | &self.file.nodes[self.idx as usize] | ||
53 | } | ||
54 | |||
55 | fn as_node(&self, idx: Option<u32>) -> Option<Node<'f>> { | ||
56 | idx.map(|idx| Node { file: self.file, idx }) | ||
57 | } | ||
58 | } | ||
59 | |||
60 | impl<'f> Iterator for Children<'f> { | ||
61 | type Item = Node<'f>; | ||
62 | |||
63 | fn next(&mut self) -> Option<Node<'f>> { | ||
64 | let next = self.next; | ||
65 | self.next = next.and_then(|node| node.as_node(node.data().next_sibling)); | ||
66 | next | ||
67 | } | ||
68 | } | ||