From 87cfe854aca3ec9e9d6158996ac03f8e4e0780fa Mon Sep 17 00:00:00 2001 From: greg Date: Fri, 6 Oct 2017 20:28:07 -0700 Subject: [PATCH] Tuple literals --- src/schala_lang/parsing.rs | 29 ++++++++++++++++++++++++----- 1 file changed, 24 insertions(+), 5 deletions(-) diff --git a/src/schala_lang/parsing.rs b/src/schala_lang/parsing.rs index ecc9613..5aa09bd 100644 --- a/src/schala_lang/parsing.rs +++ b/src/schala_lang/parsing.rs @@ -307,7 +307,8 @@ prefix_expr := prefix_op primary prefix_op := '+' | '-' | '!' | '~' primary := literal | paren_expr | if_expr | match_expr | identifier_expr -paren_expr := LParen expression RParen +paren_expr := LParen paren_inner RParen +paren_inner := (expression ',')* identifier_expr := call_expr | index_expr | IDENTIFIER literal := 'true' | 'false' | number_literal | STR_LITERAL @@ -452,6 +453,7 @@ pub enum ExpressionType { BoolLiteral(bool), BinExp(Operation, Box, Box), PrefixExp(Operation, Box), + TupleLiteral(Vec), Variable(Rc), Call { name: Rc, @@ -740,10 +742,13 @@ impl Parser { }); parse_method!(paren_expr(&mut self) -> ParseResult { - expect!(self, LParen, "'('"); - let expr = self.expression()?; - expect!(self, RParen, "')'"); - Ok(expr) + use self::ExpressionType::*; + let mut inner = delimited!(self, LParen, '(', expression, Comma, RParen, ')'); + match inner.len() { + 0 => Ok(Expression(TupleLiteral(vec![]), None)), + 1 => Ok(inner.pop().unwrap()), + _ => Ok(Expression(TupleLiteral(inner), None)), + } }); parse_method!(identifier_expr(&mut self) -> ParseResult { @@ -1002,6 +1007,20 @@ mod parse_tests { parse_test!(".1 + .2", AST(vec![exprstatement!(binexp!("+", FloatLiteral(0.1), FloatLiteral(0.2)))])); } + #[test] + fn parsing_tuples() { + parse_test!("()", AST(vec![exprstatement!(TupleLiteral(vec![]))])); + parse_test!("(\"hella\", 34)", AST(vec![exprstatement!( + TupleLiteral( + vec![ex!(StringLiteral(rc!(hella))), ex!(IntLiteral(34))] + ) + )])); + parse_test!("((1+2), \"slough\")", AST(vec![exprstatement!(TupleLiteral(vec![ + ex!(binexp!("+", IntLiteral(1), IntLiteral(2))), + ex!(StringLiteral(rc!(slough))), + ]))])) + } + #[test] fn parsing_identifiers() { parse_test!("a", AST(vec![exprstatement!(var!("a"))]));