type annotations on lambdas
This commit is contained in:
parent
a74e09c761
commit
5953d9d815
@ -111,6 +111,7 @@ pub enum ExpressionType {
|
||||
},
|
||||
Lambda {
|
||||
params: Vec<FormalParam>,
|
||||
type_anno: Option<TypeIdentifier>,
|
||||
body: Block,
|
||||
},
|
||||
ListLiteral(Vec<Expression>),
|
||||
|
@ -188,7 +188,7 @@ typed_identifier := IDENTIFIER type_anno
|
||||
func_declaration := func_signature func_body
|
||||
func_body := ε | nonempty_func_body
|
||||
nonempty_func_body := '{' (statement delimiter)* '}'
|
||||
func_signature := 'fn' func_name formal_param_list func_body
|
||||
func_signature := 'fn' func_name formal_param_list type_anno+
|
||||
func_name := IDENTIFIER | operator
|
||||
formal_param_list := '(' (formal_param ',')* ')'
|
||||
formal_param := IDENTIFIER type_anno+
|
||||
@ -227,7 +227,7 @@ primary := literal | paren_expr | if_expr | for_expr | while_expr | identifier_e
|
||||
/* Primary Expressions */
|
||||
|
||||
list_expr := '[' (expression, ',')* ']'
|
||||
lambda_expr := '\' formal_param_list nonempty_func_body
|
||||
lambda_expr := '\' formal_param_list type_anno+ nonempty_func_body
|
||||
paren_expr := LParen paren_inner RParen
|
||||
paren_inner := (expression ',')*
|
||||
identifier_expr := named_struct | IDENTIFIER
|
||||
@ -639,22 +639,12 @@ impl Parser {
|
||||
fn lambda_expr(&mut self) -> ParseResult<Expression> {
|
||||
expect!(self, Backslash);
|
||||
let params = self.formal_param_list()?; //TODO make this allow some more concise syntaxes
|
||||
let type_anno = match self.peek() {
|
||||
Colon => Some(self.type_anno()?),
|
||||
_ => None,
|
||||
};
|
||||
let body = self.nonempty_func_body()?;
|
||||
/*
|
||||
let mut body = Vec::new();
|
||||
loop {
|
||||
match self.peek() {
|
||||
EOF | RCurlyBrace => break,
|
||||
Newline | Semicolon => {
|
||||
self.next();
|
||||
continue;
|
||||
},
|
||||
_ => body.push(self.statement()?),
|
||||
}
|
||||
}
|
||||
expect!(self, RCurlyBrace);
|
||||
*/
|
||||
Ok(Expression(ExpressionType::Lambda { params, body }, None)) //TODO need to handle types somehow
|
||||
Ok(Expression(ExpressionType::Lambda { params, type_anno, body }, None)) //TODO need to handle types somehow
|
||||
}
|
||||
|
||||
#[recursive_descent_method]
|
||||
@ -1483,20 +1473,36 @@ fn a(x) {
|
||||
#[test]
|
||||
fn parsing_lambdas() {
|
||||
parse_test! { r#"\(x) { x + 1}"#, single_expr!(
|
||||
Lambda { params: vec![(rc!(x), None)], body: vec![exst!("+", val!("x"), NatLiteral(1))] }
|
||||
Lambda { params: vec![(rc!(x), None)], type_anno: None, body: vec![exst!("+", val!("x"), NatLiteral(1))] }
|
||||
) }
|
||||
|
||||
parse_test!(r#"\ (x: Int, y) { a;b;c;}"#, AST(vec![
|
||||
exprstatement!(Lambda {
|
||||
params: vec![(rc!(x), Some(ty!("Int"))), (rc!(y), None)],
|
||||
type_anno: None,
|
||||
body: vec![exst!(val!("a")), exst!(val!("b")), exst!(val!("c"))]
|
||||
})
|
||||
]));
|
||||
|
||||
parse_test!(r#"\(x){y}(1)"#, AST(vec![
|
||||
exprstatement!(Call { f: bx!(ex!(
|
||||
Lambda { params: vec![(rc!(x), None)], body: vec![exprstatement!(val!("y"))] })),
|
||||
Lambda {
|
||||
params: vec![(rc!(x), None)],
|
||||
type_anno: None,
|
||||
body: vec![exprstatement!(val!("y"))] }
|
||||
)),
|
||||
arguments: vec![ex!(NatLiteral(1))] })]));
|
||||
|
||||
parse_test! {
|
||||
r#"\(x: Int): String { "q" }"#,
|
||||
AST(vec![
|
||||
exprstatement!(Lambda {
|
||||
params: vec![(rc!(x), Some(ty!("Int")))],
|
||||
type_anno: Some(ty!("String")),
|
||||
body: vec![exprstatement!(StringLiteral(rc!(q)))]
|
||||
})
|
||||
])
|
||||
}
|
||||
}
|
||||
|
||||
#[test]
|
||||
|
Loading…
Reference in New Issue
Block a user