1use core::fmt;
2
3use enum_as_inner::EnumAsInner;
4
5use crate::identifier::IdentifierAccess;
6
7#[derive(Debug, Clone, Default, EnumAsInner)]
8pub enum Expression {
9 IntegerLiteral(IntegerLiteral),
10 FloatLiteral(FloatLiteral),
11 StringLiteral(StringLiteral),
12 BooleanLiteral(BooleanLiteral),
13 Parentheses(Parentheses),
14 UnaryOperation(UnaryOperation),
15 BinaryOperation(BinaryOperation),
16 Identifier(IdentifierAccess),
17 #[default]
18 Null,
19}
20impl Expression {
21 pub fn is_valid(&self) -> bool {
22 if self.is_integer_literal() {
23 self.as_integer_literal().unwrap().is_valid()
24 } else if self.is_float_literal() {
25 return self.as_float_literal().unwrap().is_valid();
26 } else if self.is_string_literal() {
27 return self.as_string_literal().unwrap().is_valid();
28 } else if self.is_boolean_literal() {
29 return self.as_boolean_literal().unwrap().is_valid();
30 } else if self.is_parentheses() {
31 return self.as_parentheses().unwrap().is_valid();
32 } else if self.is_unary_operation() {
33 return self.as_unary_operation().unwrap().is_valid();
34 } else if self.is_binary_operation() {
35 return self.as_binary_operation().unwrap().is_valid();
36 } else if self.is_identifier() {
37 return self.as_identifier().unwrap().is_valid();
38 } else {
39 return false;
40 }
41 }
42}
43impl fmt::Display for Expression {
44 fn fmt(&self, fmt: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
45 if self.is_integer_literal() {
46 match write!(fmt, "{}", self.as_integer_literal().unwrap()) {
47 Ok(_) => (),
48 Err(e) => return Err(e),
49 }
50 } else if self.is_float_literal() {
51 match write!(fmt, "{}", self.as_float_literal().unwrap()) {
52 Ok(_) => (),
53 Err(e) => return Err(e),
54 }
55 } else if self.is_string_literal() {
56 match write!(fmt, "{}", self.as_string_literal().unwrap()) {
57 Ok(_) => (),
58 Err(e) => return Err(e),
59 }
60 } else if self.is_boolean_literal() {
61 match write!(fmt, "{}", self.as_boolean_literal().unwrap()) {
62 Ok(_) => (),
63 Err(e) => return Err(e),
64 }
65 } else if self.is_unary_operation() {
66 match write!(fmt, "{}", self.as_unary_operation().unwrap()) {
67 Ok(_) => (),
68 Err(e) => return Err(e),
69 }
70 } else if self.is_binary_operation() {
71 match write!(fmt, "{}", self.as_binary_operation().unwrap()) {
72 Ok(_) => (),
73 Err(e) => return Err(e),
74 }
75 } else if self.is_identifier() {
76 match write!(fmt, "{}", self.as_identifier().unwrap()) {
77 Ok(_) => (),
78 Err(e) => return Err(e),
79 }
80 }
81 Ok(())
82 }
83}
84
85#[derive(Debug, Clone, Default)]
86pub struct IntegerLiteral {
87 pub value: i64,
88}
89impl IntegerLiteral {
90 pub fn new(val: i64) -> IntegerLiteral {
91 IntegerLiteral { value: val }
92 }
93
94 pub fn is_valid(&self) -> bool {
95 true
96 }
97}
98impl fmt::Display for IntegerLiteral {
99 fn fmt(&self, fmt: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
100 match write!(fmt, "{}", self.value) {
101 Ok(_) => (),
102 Err(e) => return Err(e),
103 }
104 Ok(())
105 }
106}
107
108#[derive(Debug, Clone, Default)]
109pub struct FloatLiteral {
110 pub value: f64,
111}
112impl FloatLiteral {
113 pub fn new(val: f64) -> FloatLiteral {
114 FloatLiteral { value: val }
115 }
116
117 pub fn is_valid(&self) -> bool {
118 self.value.is_normal() || self.value == 0.0
119 }
120}
121impl fmt::Display for FloatLiteral {
122 fn fmt(&self, fmt: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
123 match write!(fmt, "{}", self.value) {
124 Ok(_) => (),
125 Err(e) => return Err(e),
126 }
127 Ok(())
128 }
129}
130
131#[derive(Debug, Clone, Default)]
132pub struct StringLiteral {
133 pub value: String,
134}
135impl StringLiteral {
136 pub fn new(val: String) -> StringLiteral {
137 StringLiteral { value: val }
138 }
139 pub fn is_valid(&self) -> bool {
140 true
141 }
142}
143impl fmt::Display for StringLiteral {
144 fn fmt(&self, fmt: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
145 match write!(fmt, "\"{}\"", self.value) {
146 Ok(_) => (),
147 Err(e) => return Err(e),
148 }
149 Ok(())
150 }
151}
152
153#[derive(Debug, Clone, Default)]
154pub struct BooleanLiteral {
155 pub value: bool,
156}
157impl BooleanLiteral {
158 pub fn new(val: bool) -> BooleanLiteral {
159 BooleanLiteral { value: val }
160 }
161
162 pub fn is_valid(&self) -> bool {
163 true
164 }
165}
166impl fmt::Display for BooleanLiteral {
167 fn fmt(&self, fmt: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
168 match write!(fmt, "{}", self.value) {
169 Ok(_) => (),
170 Err(e) => return Err(e),
171 }
172 Ok(())
173 }
174}
175
176#[derive(Debug, Clone, Default)]
177pub struct UnaryOperation {
178 pub operator: String,
179 pub term: Box<Expression>,
180}
181impl UnaryOperation {
182 pub fn new(op: String, val: Expression) -> UnaryOperation {
183 UnaryOperation {
184 operator: op,
185 term: Box::new(val),
186 }
187 }
188
189 pub fn is_valid(&self) -> bool {
190 if !["+", "-", "*", "&"].contains(&self.operator.as_str()) {
191 return false;
192 }
193 self.term.is_valid()
194 }
195}
196impl fmt::Display for UnaryOperation {
197 fn fmt(&self, fmt: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
198 match write!(fmt, "{}{}", self.operator, self.term) {
199 Ok(_) => (),
200 Err(e) => return Err(e),
201 }
202 Ok(())
203 }
204}
205
206#[derive(Debug, Clone, Default)]
207pub struct Parentheses {
208 pub value: Box<Expression>,
209}
210impl Parentheses {
211 pub fn new(expr: Expression) -> Parentheses {
212 Parentheses {
213 value: Box::new(expr),
214 }
215 }
216
217 pub fn is_valid(&self) -> bool {
218 self.value.is_valid()
219 }
220}
221impl fmt::Display for Parentheses {
222 fn fmt(&self, fmt: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
223 match write!(fmt, "({})", self.value) {
224 Ok(_) => (),
225 Err(e) => return Err(e),
226 }
227 Ok(())
228 }
229}
230
231#[derive(Debug, Clone, Default)]
232pub struct BinaryOperation {
233 pub left: Box<Expression>,
234 pub operator: String,
235 pub right: Box<Expression>,
236}
237impl BinaryOperation {
238 pub fn new(left: Expression, op: String, right: Expression) -> BinaryOperation {
239 BinaryOperation {
240 left: Box::new(left),
241 operator: op,
242 right: Box::new(right),
243 }
244 }
245
246 pub fn is_valid(&self) -> bool {
247 self.left.is_valid()
248 && self.right.is_valid()
249 && ["+", "-", "*", "/", "==", "<", "<=", ">", ">=", "&&", "||"]
250 .contains(&self.operator.as_str())
251 }
252}
253impl fmt::Display for BinaryOperation {
254 fn fmt(&self, fmt: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
255 match write!(fmt, "{} {} {}", self.left, self.operator, self.right) {
256 Ok(_) => (),
257 Err(e) => return Err(e),
258 }
259 Ok(())
260 }
261}