You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

94 lines
2.8 KiB

use std::{collections::HashMap, rc::Rc};
use crate::{
exec::{DeBrujinAst as DBAst, builtin_definitions::AddOp},
parse::{Ast, Constant},
types::{PrimitiveType, Type},
};
use super::builtins::Builtin;
#[test]
fn to_de_brujin_ast_simple() {
let input = Ast::Abstraction(
"x".to_string(),
Some(Type::Primitive(PrimitiveType::Nat).into()),
Box::new(Ast::Abstraction(
"x".to_string(),
Some(Type::Primitive(PrimitiveType::Nat).into()),
Box::new(Ast::Variable("x".to_string())),
)),
);
let de_brujin: DBAst = input.into();
assert_eq!(
de_brujin,
DBAst::Abstraction(
"x".to_string(),
Some(Type::Primitive(PrimitiveType::Nat).into()),
Box::new(DBAst::Abstraction(
"x".to_string(),
Some(Type::Primitive(PrimitiveType::Nat).into()),
Box::new(DBAst::BoundVariable(1))
))
)
)
}
#[test]
fn de_brujin_beta_reduce() {
let input = Ast::Application(
Box::new(Ast::Abstraction(
"x".to_string(),
Some(Type::arrow(PrimitiveType::Nat, PrimitiveType::Nat).into()),
Box::new(Ast::Application(
Box::new(Ast::Variable("x".to_string())),
Box::new(Ast::Constant(Constant::Nat(5))),
)),
)),
Box::new(Ast::Variable("y".to_string())),
);
let dbast: DBAst = input.into();
let reduced = dbast.beta_reduce();
assert_eq!(
reduced,
DBAst::Application(
Box::new(DBAst::FreeVariable("y".to_string())),
Box::new(DBAst::Constant(Constant::Nat(5))),
),
)
}
#[test]
fn to_and_from_de_brujin_is_id() {
let input = Ast::Application(
Box::new(Ast::Abstraction(
"x".to_string(),
Some(Type::arrow(PrimitiveType::Nat, PrimitiveType::Nat).into()),
Box::new(Ast::Application(
Box::new(Ast::Variable("x".to_string())),
Box::new(Ast::Constant(Constant::Nat(5))),
)),
)),
Box::new(Ast::Variable("y".to_string())),
);
let dbast: DBAst = input.clone().into();
let output: Ast = dbast.into();
assert_eq!(input, output);
}
#[test]
fn reduce_add() {
let input: DBAst = Ast::Application(
Box::new(Ast::Application(
Box::new(Ast::Variable("add".to_string())),
Box::new(Ast::Constant(Constant::Nat(5))),
)),
Box::new(Ast::Constant(Constant::Nat(5))),
)
.into();
let mut builtins: HashMap<String, Rc<dyn Builtin>> = HashMap::new();
builtins.insert("add".to_string(), Rc::new(AddOp));
let output = input.reduce_builtins(&builtins);
assert_eq!(output, DBAst::Constant(Constant::Nat(10)));
}