Some basic pattern stuff

This commit is contained in:
greg 2018-07-01 01:26:19 -07:00
parent 46b6aeb4db
commit 55a8cabd7c
2 changed files with 66 additions and 8 deletions

View File

@ -131,9 +131,19 @@ pub struct Guard {
}
#[derive(Debug, PartialEq, Clone)]
pub struct Pattern {
pub free_vars: Vec<Rc<String>>,
pub var: Variant,
pub enum Pattern {
TuplePattern(Vec<Pattern>),
Literal(PatternLiteral),
TupleStruct(Rc<String>, Vec<Pattern>),
Record(Rc<String>, Vec<(Rc<String>, Pattern)>),
}
#[derive(Debug, PartialEq, Clone)]
pub enum PatternLiteral {
NumPattern(ExpressionType),
StringPattern(Rc<String>),
BoolPattern(bool),
VarPattern(Rc<String>)
}
#[derive(Debug, PartialEq, Clone)]

View File

@ -107,10 +107,17 @@ else_clause := ε | 'else' block
match_expr := 'match' expression match_body
match_body := '{' (match_arm)* '}'
match_arm := pattern '=>' expression
pattern := identifier //TODO NOT DONE
/* NEW GOOD */
/* Pattern syntax */
pattern := '(' (pattern, ',')* ')' | simple_pattern
simple_pattern := pattern_literal | record_pattern | tuple_struct_pattern
pattern_literal := 'true' | 'false' | number_literal | STR_LITERAL | IDENTIFIER
record_pattern := IDENTIFIER '{' (record_pattern_entry, ',')* '}'
record_pattern_entry := ???
tuple_struct_pattern := IDENTIFIER '(' (pattern, ',')* ')'
/* Expression - If */
if_expr := 'if' discriminator ('then' condititional | 'is' simple_pattern_match | guard_block)
discriminator := modified_precedence_expression
@ -678,10 +685,51 @@ impl Parser {
});
parse_method!(pattern(&mut self) -> ParseResult<Pattern> {
let identifier = self.identifier()?;
Ok(Pattern {
free_vars: vec![],
var: Variant::UnitStruct(identifier)
if let LParen = self.peek() {
let tuple_pattern_variants = delimited!(self, LParen, pattern, Comma, RParen);
Ok(Pattern::TuplePattern(tuple_pattern_variants))
} else {
self.simple_pattern()
}
});
parse_method!(simple_pattern(&mut self) -> ParseResult<Pattern> {
/*
let name = self.identifier()?;
match self.peek() {
LParen => {
let tuple_members = delimited!(self, LParen, type_name, Comma, RParen);
Ok(TupleStruct(name, tuple_members))
},
LCurlyBrace => {
let typed_identifier_list = delimited!(self, LCurlyBrace, typed_identifier, Comma, RCurlyBrace);
Ok(Record(name, typed_identifier_list))
},
_ => Ok(UnitStruct(name))
}
*/
Ok(match self.peek() {
Identifier(_) => {
let id = self.identifier()?;
match self.peek() {
LCurlyBrace => { unimplemented!() },
LParen => {
let members = delimited!(self, LParen, pattern, Comma, RParen);
Pattern::TupleStruct(id, members)
},
_ => Pattern::Literal(PatternLiteral::VarPattern(id))
}
},
Keyword(Kw::True) => Pattern::Literal(PatternLiteral::BoolPattern(true)),
Keyword(Kw::False) => Pattern::Literal(PatternLiteral::BoolPattern(false)),
StrLiteral(s) => Pattern::Literal(PatternLiteral::StringPattern(s)),
DigitGroup(_) | HexLiteral(_) | BinNumberSigil | Period => {
//TODO handle negatives
let Expression(expr_type, _) = self.number_literal()?;
Pattern::Literal(PatternLiteral::NumPattern(expr_type))
},
other => return ParseError::new(&format!("{:?} is not a valid Pattern", other))
})
});