lib/
lib.rs

1use std::cell::RefCell;
2use std::rc::{Rc, Weak};
3
4pub fn add(left: u64, right: u64) -> u64 {
5    left + right
6}
7
8struct RootNode {
9    children: Vec<TreeNode>,
10}
11
12#[derive(Debug)]
13pub struct TreeNode {
14    expanded_name: String,
15    short_name: String,
16    parent: Option<Rc<RefCell<TreeNode>>>,
17    children: Vec<Rc<RefCell<TreeNode>>>,
18}
19
20impl TreeNode {
21    pub fn new(expanded_name: String, short_name: String) -> Rc<RefCell<Self>> {
22        Rc::new(RefCell::new(Self {
23            expanded_name,
24            short_name,
25            parent: None,
26            children: Vec::new(),
27        }))
28    }
29
30    pub fn dbg(&self) {
31        for child in self.children.iter() {
32            print!("{} ", child.borrow().expanded_name);
33        }
34        println!();
35        for child in self.children.iter() {
36            child.borrow().dbg();
37        }
38    }
39
40    pub fn new_with_parent(
41        expanded_name: String,
42        short_name: String,
43        parent: Rc<RefCell<TreeNode>>,
44    ) -> Rc<RefCell<Self>> {
45        let ret = Rc::new(RefCell::new(Self {
46            expanded_name,
47            short_name,
48            parent: Some(Rc::clone(&parent)),
49            children: Vec::new(),
50        }));
51        parent.borrow_mut().children.push(Rc::clone(&ret));
52        ret
53    }
54}
55
56pub struct TreeCursor {
57    cur_ast_pos: Weak<RefCell<TreeNode>>,
58    input_buf: String,
59}
60
61impl TreeCursor {
62    pub fn new(ast_root: &Rc<RefCell<TreeNode>>) -> Self {
63        Self {
64            cur_ast_pos: Rc::downgrade(ast_root),
65            input_buf: String::new(),
66        }
67    }
68    pub fn advance(&mut self, input: char) -> Result<(), String> {
69        self.input_buf.push(input);
70        // println!("Input buf: {}", self.input_buf);
71        let binding = self.cur_ast_pos.upgrade().expect("Tree failure");
72        let borrow = binding.borrow();
73        let possibly_next_node = borrow
74            .children
75            .iter()
76            .find(|child| child.borrow().short_name == self.input_buf);
77        if let Some(next_node) = possibly_next_node {
78            // println!("Found: {}", next_node.borrow().expanded_name);
79            let next_node = Rc::clone(&next_node);
80            self.cur_ast_pos = Rc::downgrade(&Rc::clone(&next_node));
81            self.input_buf.clear();
82        }
83        Ok(())
84    }
85    fn dump(&self) {
86        println!(
87            "Last matched node: {}",
88            self.cur_ast_pos.upgrade().unwrap().borrow().expanded_name
89        );
90        println!("Input buf: {}", self.input_buf);
91    }
92    pub fn get_last_matched_node(&self) -> String {
93        self.cur_ast_pos
94            .upgrade()
95            .unwrap()
96            .borrow()
97            .expanded_name
98            .clone()
99    }
100    pub fn is_done(&self) -> bool {
101        self.cur_ast_pos
102            .upgrade()
103            .unwrap()
104            .borrow()
105            .children
106            .is_empty()
107    }
108}
109
110#[cfg(test)]
111mod tests {
112    use super::*;
113
114    #[test]
115    fn it_works() {
116        let result = add(2, 2);
117        assert_eq!(result, 4);
118    }
119
120    #[test]
121    fn simple_tree() {
122        let root = TreeNode::new("int".to_string(), "i".to_string());
123        let _other = TreeNode::new_with_parent("asdf".to_string(), "a".to_string(), root.clone());
124        assert_eq!(root.borrow().children.len(), 1);
125    }
126
127    #[test]
128    fn simple_cursor_steps() {
129        let root = TreeNode::new("BEGIN".to_string(), String::new());
130        let second = TreeNode::new_with_parent("int".to_string(), "i".to_string(), root.clone());
131        TreeNode::new_with_parent("asdf".to_string(), "a".to_string(), second.clone());
132        let mut cursor = TreeCursor {
133            cur_ast_pos: Rc::downgrade(&root),
134            input_buf: String::new(),
135        };
136        assert_eq!(cursor.get_last_matched_node(), "BEGIN");
137        cursor.advance('i').unwrap();
138        assert_eq!(cursor.get_last_matched_node(), "int");
139        cursor.advance('a').unwrap();
140        assert_eq!(cursor.get_last_matched_node(), "asdf");
141    }
142}