mate_rs/
monitor.rs

1//
2// Copyright 2022-present theiskaa. All rights reserved.
3// Use of this source code is governed by MIT license
4// that can be found in the LICENSE file.
5//
6
7use crate::token::{Sub, SubMethod, Token, TokenType};
8
9pub trait Monitor {
10    // Converts the [&self] object to the
11    // right String representing value.
12    fn to_string(&self, n: usize) -> String;
13}
14
15// A monitor debugger implementation for [Token].
16impl Monitor for Token {
17    fn to_string(&self, n: usize) -> String {
18        let mut lit: String;
19        let mut space: String = String::new();
20
21        let nest: usize = n;
22        if self.typ != TokenType::SUBEXP {
23            lit = format!("({})", self.literal.to_string());
24        } else {
25            lit = String::new();
26            for t in self.sub.tokens.iter().map(|t| t.to_string(nest + 1)) {
27                lit.push_str(format!("\n{}", t).as_str())
28            }
29        }
30
31        for _ in 0..nest {
32            space.push_str("  ");
33        }
34
35        let mut typstr = self.typ.to_string(0);
36        if self.is_sub_exp() {
37            typstr.push_str(format!(" -> {{{}}}", self.sub.to_string(0)).as_str());
38        }
39
40        format!("{}{}{}", space.as_str(), typstr, lit)
41    }
42}
43
44// A monitor debugger implementation for [TokenType].
45impl Monitor for TokenType {
46    fn to_string(&self, _n: usize) -> String {
47        let data = match self {
48            TokenType::NUMBER => "NUMBER",
49            TokenType::ILLEGAL => "ILLEGAL",
50            TokenType::SUBEXP => "SUB-EXPRESSION",
51            TokenType::LPAREN => "LEFT-PARENTHESES",
52            TokenType::RPAREN => "RIGHT-PARENTHESES",
53            TokenType::POINTER => "POINTER",
54            TokenType::PLUS => "PLUS",
55            TokenType::MINUS => "MINUS",
56            TokenType::PRODUCT => "PRODUCT",
57            TokenType::DIVIDE => "DIVIDE",
58            TokenType::PERCENTAGE => "PERCENTAGE",
59            TokenType::POWER => "POWER",
60            TokenType::LABS => "LEFT-ABS",
61            TokenType::RABS => "RIGHT-ABS",
62        };
63
64        String::from(data)
65    }
66}
67
68// A monitor debugger implementation for [Sub].
69impl Monitor for Sub {
70    fn to_string(&self, _n: usize) -> String {
71        let data = match &self.method {
72            SubMethod::ABS => "ABSOLUTE-VALUE",
73            SubMethod::PAREN => "PARENTHESES",
74        };
75
76        String::from(data)
77    }
78}
79
80// A monitor debugger implementation for [SubMethod].
81impl Monitor for SubMethod {
82    fn to_string(&self, _n: usize) -> String {
83        let data = match self {
84            SubMethod::ABS => "ABSOLUTE-VALUE",
85            SubMethod::PAREN => "PARENTHESES",
86        };
87
88        String::from(data)
89    }
90}
91
92#[cfg(test)]
93mod tests {
94    use super::*;
95    use std::collections::HashMap;
96
97    #[test]
98    fn token_to_string() {
99        let test_data: HashMap<String, String> = HashMap::from([
100            (
101                Token::from(String::from("-25"), (0, 1)).to_string(0),
102                String::from("NUMBER(-25)"),
103            ),
104            (
105                Token::from(String::from("/"), (0, 0)).to_string(0),
106                String::from("DIVIDE(/)"),
107            ),
108        ]);
109
110        for (t, expected) in test_data {
111            assert_eq!(t, expected);
112        }
113    }
114
115    #[test]
116    fn token_type_to_string() {
117        let test_data: HashMap<String, &str> = HashMap::from([
118            (TokenType::NUMBER.to_string(0), "NUMBER"),
119            (TokenType::ILLEGAL.to_string(0), "ILLEGAL"),
120            (TokenType::SUBEXP.to_string(0), "SUB-EXPRESSION"),
121            (TokenType::LPAREN.to_string(0), "LEFT-PARENTHESES"),
122            (TokenType::RPAREN.to_string(0), "RIGHT-PARENTHESES"),
123            (TokenType::POINTER.to_string(0), "POINTER"),
124            (TokenType::PLUS.to_string(0), "PLUS"),
125            (TokenType::MINUS.to_string(0), "MINUS"),
126            (TokenType::PRODUCT.to_string(0), "PRODUCT"),
127            (TokenType::DIVIDE.to_string(0), "DIVIDE"),
128            (TokenType::PERCENTAGE.to_string(0), "PERCENTAGE"),
129            (TokenType::POWER.to_string(0), "POWER"),
130            (TokenType::LABS.to_string(0), "LEFT-ABS"),
131            (TokenType::RABS.to_string(0), "RIGHT-ABS"),
132        ]);
133
134        for (tt, expected) in test_data {
135            assert_eq!(tt, expected);
136        }
137    }
138
139    #[test]
140    fn sub_to_string() {
141        let test_data: HashMap<String, &str> = HashMap::from([
142            (
143                Sub::new(Vec::new(), SubMethod::PAREN).to_string(0),
144                "PARENTHESES",
145            ),
146            (
147                Sub::new(Vec::new(), SubMethod::ABS).to_string(0),
148                "ABSOLUTE-VALUE",
149            ),
150        ]);
151
152        for (s, expected) in test_data {
153            assert_eq!(s, expected);
154        }
155    }
156
157    #[test]
158    fn sub_type_to_string() {
159        let test_data: HashMap<String, &str> = HashMap::from([
160            (SubMethod::PAREN.to_string(0), "PARENTHESES"),
161            (SubMethod::ABS.to_string(0), "ABSOLUTE-VALUE"),
162        ]);
163
164        for (s, expected) in test_data {
165            assert_eq!(s, expected);
166        }
167    }
168}