elo_rust/codegen/
operators.rs1use proc_macro2::TokenStream;
4use quote::quote;
5
6#[derive(Debug, Clone, Copy, PartialEq, Eq)]
10pub enum BinaryOp {
11 Equal,
13 NotEqual,
15 Less,
17 LessEqual,
19 Greater,
21 GreaterEqual,
23 And,
25 Or,
27 Add,
29 Subtract,
31 Multiply,
33 Divide,
35 Modulo,
37}
38
39#[derive(Debug, Clone, Copy, PartialEq, Eq)]
43pub enum UnaryOp {
44 Not,
46 Negate,
48}
49
50#[derive(Debug, Clone)]
54pub struct OperatorGenerator;
55
56impl OperatorGenerator {
57 pub fn new() -> Self {
59 Self
60 }
61
62 pub fn binary(&self, op: BinaryOp, left: TokenStream, right: TokenStream) -> TokenStream {
74 match op {
75 BinaryOp::Equal => quote! { #left == #right },
76 BinaryOp::NotEqual => quote! { #left != #right },
77 BinaryOp::Less => quote! { #left < #right },
78 BinaryOp::LessEqual => quote! { #left <= #right },
79 BinaryOp::Greater => quote! { #left > #right },
80 BinaryOp::GreaterEqual => quote! { #left >= #right },
81 BinaryOp::Add => quote! { #left + #right },
82 BinaryOp::Subtract => quote! { #left - #right },
83 BinaryOp::Multiply => quote! { #left * #right },
84 BinaryOp::Divide => quote! { #left / #right },
85 BinaryOp::Modulo => quote! { #left % #right },
86 BinaryOp::And => quote! { #left && #right },
87 BinaryOp::Or => quote! { #left || #right },
88 }
89 }
90
91 pub fn unary(&self, op: UnaryOp, operand: TokenStream) -> TokenStream {
102 match op {
103 UnaryOp::Not => quote! { !#operand },
104 UnaryOp::Negate => quote! { -#operand },
105 }
106 }
107}
108
109impl Default for OperatorGenerator {
110 fn default() -> Self {
111 Self::new()
112 }
113}
114
115#[cfg(test)]
116mod tests {
117 use super::*;
118
119 #[test]
120 fn test_binary_op_equality() {
121 assert_eq!(BinaryOp::Equal, BinaryOp::Equal);
122 assert_ne!(BinaryOp::Equal, BinaryOp::NotEqual);
123 }
124
125 #[test]
126 fn test_binary_op_comparison() {
127 assert_ne!(BinaryOp::Less, BinaryOp::Greater);
128 assert_eq!(BinaryOp::LessEqual, BinaryOp::LessEqual);
129 }
130
131 #[test]
132 fn test_binary_op_logical() {
133 assert_eq!(BinaryOp::And, BinaryOp::And);
134 assert_ne!(BinaryOp::And, BinaryOp::Or);
135 }
136
137 #[test]
138 fn test_unary_op_not() {
139 assert_eq!(UnaryOp::Not, UnaryOp::Not);
140 assert_ne!(UnaryOp::Not, UnaryOp::Negate);
141 }
142
143 #[test]
144 fn test_operator_generator_creation() {
145 let _gen = OperatorGenerator::new();
146 }
147}