diff options
author | Joel Kronqvist <joel.kronqvist@iki.fi> | 2025-08-10 14:36:02 +0300 |
---|---|---|
committer | Joel Kronqvist <joel.kronqvist@iki.fi> | 2025-08-10 14:36:02 +0300 |
commit | c121f20620499e9b7c497c82c7321474cbf59e1d (patch) | |
tree | 617c20d31cb577b459a423074d97a6e1b91e2a0c /src/type/conversion.rs | |
parent | 09f39aebe68213799fdd7a33665a162c40baf299 (diff) | |
download | myslip-c121f20620499e9b7c497c82c7321474cbf59e1d.tar.gz myslip-c121f20620499e9b7c497c82c7321474cbf59e1d.zip |
Implemented aka. Changed Nil:st type to NilType from an empty list.
Diffstat (limited to 'src/type/conversion.rs')
-rw-r--r-- | src/type/conversion.rs | 55 |
1 files changed, 50 insertions, 5 deletions
diff --git a/src/type/conversion.rs b/src/type/conversion.rs index 128d1aa..a819409 100644 --- a/src/type/conversion.rs +++ b/src/type/conversion.rs @@ -1,5 +1,5 @@ -use crate::r#type::Type; +use crate::r#type::{Type, Type::*, util::*}; impl Type { @@ -27,11 +27,48 @@ impl Type { /// assert!(!List(vec![Integer, Boolean]).aka(&vecof(Boolean))); /// ``` pub fn aka(&self, known_as: &Type) -> bool { - todo!() + self.least_general_supertype(known_as) == *known_as } fn least_general_supertype(&self, other: &Type) -> Type { - todo!() + + match (self, other) { + + (a, b) if a == b => a.clone(), + + (VecOf(a), VecOf(b)) => vecof(a.least_general_supertype(b)), + + (List(v1), List(v2)) if v1.len() == v2.len() => { + let mut res = vec![]; + for (a, b) in v1.into_iter().zip(v2) { + res.push(a.least_general_supertype(b)); + } + List(res) + }, + + (List(v1), List(v2)) => match v1.get(0).or(v2.get(0)) { + Some(first) => vecof( + v1.into_iter() + .chain(v2) + .fold(first.clone(), |a, b| a.least_general_supertype(b)) + ), + None => panic!("unreachable - types would be equal") + }, + + (List(v), VecOf(b)) => vecof( + v.into_iter() + .fold(*b.clone(), |a, b| a.least_general_supertype(b)) + ), + (VecOf(b), List(v)) => vecof( + v.into_iter() + .fold(*b.clone(), |a, b| a.least_general_supertype(b)) + ), + + + _ => vt("T") + + } + } } @@ -44,8 +81,16 @@ mod tests { #[test] fn test_basic_general_supertypes() { - assert_eq!(Integer.least_general_supertype(&Integer), Integer); - assert_eq!(Integer.least_general_supertype(&Boolean), vt("T")); + assert_eq!( + Integer.least_general_supertype(&Integer), + Integer, + "if two types are equal, they get the same supertype" + ); + assert_eq!( + Integer.least_general_supertype(&Boolean), + vt("T"), + "if two types have nothing in common, vt(\"t\") is returned" + ); } |