avid/
typing.rs

1use std::fmt;
2
3type VecObj = Vec<Object>;
4
5enum_type! {
6    /// The possible types in an Avid program.
7    Object {
8        /// A number.
9        Num(isize),
10        /// A string
11        String(String),
12        /// A boolean
13        Bool(bool),
14        /// A list of objects
15        List(VecObj)
16    }
17}
18
19impl Clone for Object {
20    fn clone(&self) -> Self {
21        match self {
22            Self::Num(i) => Self::Num(*i),
23            Self::String(s) => Self::String(s.clone()),
24            Self::Bool(b) => Self::Bool(*b),
25            Self::List(l) => Self::List(l.clone()),
26        }
27    }
28}
29
30impl Object {
31    /// Whether the object evaluates to "true" in a condition.
32    ///
33    /// For now, the only instances that evaluate to `false` are `false`, `""` and
34    /// `0`.
35    pub fn truthy(&self) -> bool {
36        let cond = match self {
37            Object::Num(n) => *n == 0,
38            Object::String(s) => s.as_str() == "",
39            Object::Bool(b) => !*b,
40            Object::List(l) => l.is_empty(),
41        };
42        !cond
43    }
44}
45
46impl fmt::Display for Object {
47    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
48        match self {
49            Self::Num(n) => write!(f, "{n}"),
50            Self::String(s) => write!(f, "{s}"),
51            Self::Bool(b) => write!(f, "{b}"),
52            Self::List(l) => {
53                write!(f, "[")?;
54                for (idx, obj) in l.iter().enumerate() {
55                    if idx > 0 {
56                        write!(f, ", ")?;
57                    }
58                    write!(f, "{obj}")?;
59                }
60                write!(f, "]")
61            }
62        }
63    }
64}