1mod display;
2pub mod valuetype;
3
4use self::valuetype::ValueType;
5use super::out::*;
6use crate::{settings::Rounding, token::tokentype::TokenType};
7use num::complex::Complex64;
8
9pub type IntValue = i64;
10pub type FloatValue = f64;
11pub type ComplexValue = Complex64;
12pub type VectorValue = Vec<Value>;
13pub type BoolValue = bool;
14
15#[derive(Debug, Clone)]
17#[cfg_attr(feature = "serde", derive(serde::Serialize, serde::Deserialize))]
18pub enum Value {
19 Int(IntValue),
20 Float(FloatValue),
21 Complex(ComplexValue),
22 Vector(VectorValue),
23 Bool(BoolValue),
24}
25
26impl Value {
27 pub fn get_type(&self) -> ValueType {
28 match self {
29 Value::Float(_) => ValueType::FloatType,
30 Value::Int(_) => ValueType::IntType,
31 Value::Complex(_) => ValueType::ComplexType,
32 Value::Vector(_) => ValueType::VectorType,
33 Value::Bool(_) => ValueType::BoolType,
34 }
35 }
36
37 pub fn is_int(&self) -> bool {
38 matches!(self, Value::Int(_))
39 }
40
41 pub fn is_float(&self) -> bool {
42 matches!(self, Value::Float(_))
43 }
44
45 pub fn is_complex(&self) -> bool {
46 matches!(self, Value::Complex(_))
47 }
48
49 pub fn is_vector(&self) -> bool {
50 matches!(self, Value::Vector(_))
51 }
52
53 pub fn is_bool(&self) -> bool {
54 matches!(self, Value::Bool(_))
55 }
56
57 pub fn as_int(&self) -> EvalResult<IntValue> {
58 match self {
59 Value::Int(n) => Ok(*n),
60 Value::Float(n) => {
61 if n.fract() == 0.0 {
62 Ok(*n as IntValue)
63 } else {
64 Err(ErrorType::FailedCast {
65 value: self.clone(),
66 from: ValueType::FloatType,
67 to: ValueType::IntType,
68 })
69 }
70 }
71 Value::Bool(n) => Ok(*n as i64),
72 _ => match self.as_float() {
73 Ok(float) => Value::Float(float).as_int(),
74 Err(err) => match err {
76 ErrorType::FailedCast { value, from, to: _ } => Err(ErrorType::FailedCast {
77 value,
78 from,
79 to: ValueType::IntType,
80 }),
81 other => Err(other),
82 },
83 },
84 }
85 }
86
87 pub fn as_float(&self) -> EvalResult<FloatValue> {
88 match self {
89 Value::Float(n) => Ok(*n),
90 Value::Int(n) => Ok(*n as f64),
91 Value::Bool(n) => Ok(*n as i64 as f64),
92 Value::Complex(n) => {
93 if n.im == 0.0 {
94 Ok(n.re)
95 } else {
96 Err(ErrorType::FailedCast {
97 value: self.clone(),
98 from: ValueType::ComplexType,
99 to: ValueType::FloatType,
100 })
101 }
102 }
103 _ => match self.as_complex() {
104 Ok(complex) => Value::Complex(complex).as_float(),
105 Err(err) => match err {
107 ErrorType::FailedCast { value, from, to: _ } => Err(ErrorType::FailedCast {
108 value,
109 from,
110 to: ValueType::FloatType,
111 }),
112 other => Err(other),
113 },
114 },
115 }
116 }
117
118 pub fn as_complex(&self) -> EvalResult<ComplexValue> {
119 match self {
120 Value::Complex(n) => Ok(*n),
121 Value::Float(n) => Ok(Complex64::new(*n, 0.0)),
122 Value::Int(n) => Ok(Complex64::new(*n as f64, 0.0)),
123 Value::Bool(n) => Ok(Complex64::new(*n as i64 as f64, 0.0)),
124 Value::Vector(v) => {
125 if v.len() == 1 {
126 v[0].as_complex()
127 } else {
128 Err(ErrorType::FailedCast {
129 value: self.clone(),
130 from: ValueType::VectorType,
131 to: ValueType::ComplexType,
132 })
133 }
134 }
135 }
136 }
137
138 pub fn as_vector(&self) -> VectorValue {
139 match self {
140 Value::Vector(v) => v.clone(),
141 Value::Int(n) => vec![Value::Int(*n)],
142 Value::Float(n) => vec![Value::Float(*n)],
143 Value::Complex(n) => vec![Value::Complex(*n)],
144 Value::Bool(n) => vec![Value::Bool(*n)],
145 }
146 }
147
148 pub fn as_bool(&self) -> EvalResult<BoolValue> {
149 match self {
150 Value::Bool(n) => Ok(*n),
151 Value::Int(n) => {
152 if *n == 1 {
153 Ok(true)
154 } else if *n == 0 {
155 Ok(false)
156 } else {
157 Err(ErrorType::FailedCast {
158 value: self.clone(),
159 from: ValueType::IntType,
160 to: ValueType::BoolType,
161 })
162 }
163 }
164 _ => match self.as_int() {
165 Ok(value) => Value::Int(value).as_bool(),
166 Err(err) => match err {
168 ErrorType::FailedCast { value, from, to: _ } => Err(ErrorType::FailedCast {
169 value,
170 from,
171 to: ValueType::BoolType,
172 }),
173 other => Err(other),
174 },
175 },
176 }
177 }
178
179 pub fn as_type(&self, valuetype: &ValueType) -> EvalResult<Value> {
180 match valuetype {
181 ValueType::BoolType => Ok(Value::Bool(self.as_bool()?)),
182 ValueType::IntType => Ok(Value::Int(self.as_int()?)),
183 ValueType::FloatType => Ok(Value::Float(self.as_float()?)),
184 ValueType::ComplexType => Ok(Value::Complex(self.as_complex()?)),
185 ValueType::VectorType => Ok(Value::Vector(self.as_vector())),
186 }
187 }
188
189 pub fn from_string(string: String) -> EvalResult<Self> {
191 match &string[..] {
192 "true" => Ok(Value::Bool(true)),
193 "false" => Ok(Value::Bool(false)),
194 other => {
195 let mut other = String::from(other);
196
197 let i_count = other.matches("i").count();
199 if i_count != 0 {
200 if i_count == 1 {
201 other = String::from(other).replace("i", "");
202
203 let other = if other == "" {
204 String::from("1")
205 } else {
206 other
207 };
208
209 return Ok(Value::Complex(Complex64::new(
210 0.0,
211 match other.parse::<f64>() {
212 Ok(value) => value,
213 Err(_) => return Err(ErrorType::FailedParse { value: string }),
214 },
215 )));
216 } else {
217 return Err(ErrorType::FailedParse { value: string });
218 }
219 }
220
221 let count = other.matches(".").count();
223 if count != 0 {
224 if count == 1 {
225 match other.parse::<f64>() {
226 Ok(value) => Ok(Value::Float(value)),
227 Err(_) => Err(ErrorType::FailedParse { value: string }),
228 }
229 } else {
230 Err(ErrorType::InvalidTokenPosition {
231 token: TokenType::Dot,
232 })
233 }
234 } else {
235 match other.parse::<i64>() {
236 Ok(value) => Ok(Value::Int(value)),
237 Err(_) => Err(ErrorType::FailedParse { value: string }),
238 }
239 }
240 }
241 }
242 }
243
244 pub fn try_as_type(&self, valuetype: ValueType) -> Value {
247 if self.to_type().complexity() <= valuetype.complexity() {
249 self.clone()
250 } else {
251 match valuetype {
252 ValueType::BoolType => match self.as_bool() {
253 Ok(value) => Value::Bool(value),
254 Err(_) => self.try_as_type(ValueType::IntType),
255 },
256 ValueType::IntType => match self.as_int() {
257 Ok(value) => Value::Int(value),
258 Err(_) => self.try_as_type(ValueType::FloatType),
259 },
260 ValueType::FloatType => match self.as_float() {
261 Ok(value) => Value::Float(value),
262 Err(_) => self.try_as_type(ValueType::ComplexType),
263 },
264 ValueType::ComplexType => match self.as_complex() {
265 Ok(value) => Value::Complex(value),
266 Err(_) => self.try_as_type(ValueType::VectorType),
267 },
268 ValueType::VectorType => Value::Vector(self.as_vector()),
269 }
270 }
271 }
272
273 pub fn round(&self, rounding: Rounding) -> Self {
274 match rounding {
275 Rounding::Round(precision) => {
276 let precision = precision.clamp(0, 12);
277 let factor = (10.0f64.powi(precision as i32)) as f64;
278 match self {
279 Self::Float(v) => Value::Float((*v * factor).round() / factor),
280 Self::Complex(c) => Value::Complex(Complex64::new(
281 (c.re * factor).round() / factor,
282 (c.im * factor).round() / factor,
283 )),
284 Self::Vector(vec) => {
285 let mut out_vec = vec![];
286 for val in vec {
287 out_vec.push(val.round(rounding).clone());
288 }
289 Value::Vector(out_vec)
290 }
291 other => other.clone(),
292 }
293 }
294 _ => self.clone(),
295 }
296 }
297}
298
299impl From<BoolValue> for Value {
300 fn from(bool: BoolValue) -> Self {
301 Value::Bool(bool)
302 }
303}
304
305impl From<IntValue> for Value {
306 fn from(int: IntValue) -> Self {
307 Value::Int(int)
308 }
309}
310
311impl From<FloatValue> for Value {
312 fn from(float: FloatValue) -> Self {
313 Value::Float(float)
314 }
315}
316
317impl From<ComplexValue> for Value {
318 fn from(complex: ComplexValue) -> Self {
319 Value::Complex(complex)
320 }
321}
322
323impl<T> From<Vec<T>> for Value
324where
325 Value: From<T>,
326 T: Clone,
327{
328 fn from(vec: Vec<T>) -> Self {
329 Value::Vector(vec.iter().map(|v| Value::from(v.clone())).collect())
330 }
331}
332
333impl PartialEq for Value {
334 fn eq(&self, other: &Self) -> bool {
335 match self.clone().equal_to(other.clone()) {
338 Ok(bool_value) => bool_value.as_bool().unwrap(),
339 Err(_) => false,
340 }
341 }
342}