mirror of
https://github.com/azur1s/bobbylisp.git
synced 2024-10-16 02:37:40 -05:00
expr and block expr
This commit is contained in:
parent
fce1760198
commit
f56965bdb6
|
@ -1,2 +1,4 @@
|
|||
fun foo a b = a + b;
|
||||
fun bar a b = { a + b };
|
||||
let res = foo(34, 35);
|
||||
let res = { foo(34, 35) };
|
|
@ -54,6 +54,8 @@ pub fn lexer() -> impl Parser<char, Vec<(Token, Span)>, Error = Simple<char>> {
|
|||
let delimiter = choice((
|
||||
just('('),
|
||||
just(')'),
|
||||
just('{'),
|
||||
just('}'),
|
||||
)).map(|c| Token::Delimiter(c));
|
||||
|
||||
let symbol = choice((
|
||||
|
@ -101,12 +103,12 @@ pub enum Expr {
|
|||
|
||||
Let {
|
||||
name: String,
|
||||
value: Box<Self>,
|
||||
value: Vec<Self>,
|
||||
},
|
||||
Fun {
|
||||
name: String,
|
||||
args: Vec<String>,
|
||||
body: Box<Self>,
|
||||
body: Vec<Self>,
|
||||
},
|
||||
Call {
|
||||
name: Box<Self>,
|
||||
|
@ -129,7 +131,7 @@ fn expr_parser() -> impl Parser<Token, Expr, Error = Simple<Token>> + Clone {
|
|||
_ => Err(Simple::expected_input_found(span, Vec::new(), Some(token))),
|
||||
}).labelled("literal");
|
||||
|
||||
let items = expr.clone()
|
||||
let args = expr.clone()
|
||||
.chain(just(Token::Comma)
|
||||
.ignore_then(expr.clone()).repeated())
|
||||
.then_ignore(just(Token::Comma).or_not())
|
||||
|
@ -145,7 +147,7 @@ fn expr_parser() -> impl Parser<Token, Expr, Error = Simple<Token>> + Clone {
|
|||
|
||||
let call = atom
|
||||
.then(
|
||||
items
|
||||
args
|
||||
.delimited_by(
|
||||
just(Token::Delimiter('(')),
|
||||
just(Token::Delimiter(')')))
|
||||
|
@ -195,26 +197,37 @@ fn expr_parser() -> impl Parser<Token, Expr, Error = Simple<Token>> + Clone {
|
|||
}).labelled("expression");
|
||||
|
||||
let declare = recursive(|decl| {
|
||||
let decl_block = decl.clone()
|
||||
.or(expr.clone())
|
||||
.repeated()
|
||||
.delimited_by(just(Token::Delimiter('{')), just(Token::Delimiter('}')));
|
||||
|
||||
let declare_var = just(Token::Let)
|
||||
.ignore_then(ident)
|
||||
.then_ignore(just(Token::Assign))
|
||||
.then(expr.clone())
|
||||
.then(
|
||||
decl_block.clone()
|
||||
.or(decl.clone().repeated().at_most(1))
|
||||
)
|
||||
.then_ignore(just(Token::Semicolon))
|
||||
.map(|(name, rhs)| Expr::Let {
|
||||
.map(|(name, value)| Expr::Let {
|
||||
name,
|
||||
value: Box::new(rhs),
|
||||
value,
|
||||
});
|
||||
|
||||
let declare_fun = just(Token::Fun)
|
||||
.ignore_then(ident)
|
||||
.then(ident.repeated())
|
||||
.then_ignore(just(Token::Assign))
|
||||
.then(expr.clone())
|
||||
.then(
|
||||
decl_block.clone()
|
||||
.or(decl.clone().repeated().at_most(1))
|
||||
)
|
||||
.then_ignore(just(Token::Semicolon))
|
||||
.map(|((name, args), body)| Expr::Fun {
|
||||
name,
|
||||
args,
|
||||
body: Box::new(body),
|
||||
body,
|
||||
});
|
||||
|
||||
declare_var
|
||||
|
|
10
src/main.rs
10
src/main.rs
|
@ -20,10 +20,14 @@ fn main() {
|
|||
let (tokens, lex_error) = lexer().parse_recovery(src.as_str());
|
||||
let len = src.chars().count();
|
||||
let (ast, parse_error) = parser().parse_recovery(Stream::from_iter(len..len + 1, tokens.clone().unwrap().into_iter()));
|
||||
if parse_error.is_empty() {
|
||||
println!("{:#?}", ast);
|
||||
if lex_error.is_empty() {
|
||||
if parse_error.is_empty() {
|
||||
println!("{:#?}", ast);
|
||||
} else {
|
||||
eprintln!("{:#?}", parse_error);
|
||||
}
|
||||
} else {
|
||||
println!("{:?}", parse_error);
|
||||
eprintln!("{:#?}", lex_error);
|
||||
}
|
||||
},
|
||||
}
|
||||
|
|
Loading…
Reference in a new issue