Fixing for loop
This commit is contained in:
+6
-11
@@ -70,6 +70,11 @@ pub enum Statement {
|
|||||||
init: Option<Expression>,
|
init: Option<Expression>,
|
||||||
},
|
},
|
||||||
|
|
||||||
|
VarAssign {
|
||||||
|
target: Expression,
|
||||||
|
value: Expression,
|
||||||
|
},
|
||||||
|
|
||||||
// if (...) stmt else stmt
|
// if (...) stmt else stmt
|
||||||
If {
|
If {
|
||||||
condition: Expression,
|
condition: Expression,
|
||||||
@@ -85,7 +90,7 @@ pub enum Statement {
|
|||||||
|
|
||||||
// for (...) stmt
|
// for (...) stmt
|
||||||
For {
|
For {
|
||||||
init: Option<ForInit>,
|
init: (VarKind, String, Option<Expression>),
|
||||||
condition: Option<Expression>,
|
condition: Option<Expression>,
|
||||||
update: Option<Expression>,
|
update: Option<Expression>,
|
||||||
body: Box<Statement>,
|
body: Box<Statement>,
|
||||||
@@ -118,13 +123,3 @@ pub enum VarKind {
|
|||||||
Const,
|
Const,
|
||||||
Var,
|
Var,
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Debug, Clone, Serialize)]
|
|
||||||
pub enum ForInit {
|
|
||||||
VarDecl {
|
|
||||||
kind: VarKind,
|
|
||||||
name: String,
|
|
||||||
init: Option<Expression>,
|
|
||||||
},
|
|
||||||
Expr(Expression),
|
|
||||||
}
|
|
||||||
|
|||||||
@@ -39,6 +39,7 @@ statement_list = { statement* }
|
|||||||
statement = _{
|
statement = _{
|
||||||
expr_stmt
|
expr_stmt
|
||||||
| var_decl
|
| var_decl
|
||||||
|
| var_assign
|
||||||
| if_stmt
|
| if_stmt
|
||||||
| while_stmt
|
| while_stmt
|
||||||
| for_stmt
|
| for_stmt
|
||||||
@@ -66,6 +67,10 @@ var_decl = {
|
|||||||
var_decl_kind ~ identifier ~ ("=" ~ expr)? ~ ";"
|
var_decl_kind ~ identifier ~ ("=" ~ expr)? ~ ";"
|
||||||
}
|
}
|
||||||
|
|
||||||
|
var_assign = {
|
||||||
|
expr ~ "=" ~ expr ~ ";"
|
||||||
|
}
|
||||||
|
|
||||||
// --- control flow ---
|
// --- control flow ---
|
||||||
|
|
||||||
if_stmt = {
|
if_stmt = {
|
||||||
@@ -77,12 +82,11 @@ while_stmt = {
|
|||||||
}
|
}
|
||||||
|
|
||||||
for_stmt = {
|
for_stmt = {
|
||||||
"for" ~ "(" ~ (var_decl_no_semicolon | expr_stmt | ";") ~ expr? ~ ";" ~ expr? ~ ")" ~ statement
|
"for" ~ "(" ~ var_decl ~ expr ~ ";" ~ var_assign_no_semicolon ~ ")" ~ statement
|
||||||
}
|
}
|
||||||
|
|
||||||
// helper (same as var_decl but no trailing ;)
|
var_assign_no_semicolon = {
|
||||||
var_decl_no_semicolon = {
|
expr ~ "=" ~ expr
|
||||||
var_decl_kind ~ identifier ~ ("=" ~ expr)?
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// ================= EXPRESSIONS =================
|
// ================= EXPRESSIONS =================
|
||||||
|
|||||||
+32
-22
@@ -229,30 +229,32 @@ impl Statement {
|
|||||||
Rule::for_stmt => {
|
Rule::for_stmt => {
|
||||||
let mut inner = pair.into_inner();
|
let mut inner = pair.into_inner();
|
||||||
|
|
||||||
let init = inner.next().map(|p| match p.as_rule() {
|
let init = inner
|
||||||
Rule::var_decl_no_semicolon => {
|
.next()
|
||||||
let mut it = p.into_inner();
|
.map(|p| match p.as_rule() {
|
||||||
|
Rule::var_decl => {
|
||||||
|
let mut it = p.into_inner();
|
||||||
|
|
||||||
let kind = match it.next().unwrap().as_str() {
|
let kind = match it.next().unwrap().as_str() {
|
||||||
"let" => VarKind::Let,
|
"let" => VarKind::Let,
|
||||||
"const" => VarKind::Const,
|
"const" => VarKind::Const,
|
||||||
"var" => VarKind::Var,
|
"var" => VarKind::Var,
|
||||||
_ => unreachable!(),
|
_ => unreachable!(),
|
||||||
};
|
};
|
||||||
|
|
||||||
let name = it.next().unwrap().as_str().to_string();
|
let name = it.next().unwrap().as_str().to_string();
|
||||||
let init_expr = it
|
let init_expr = it
|
||||||
.next()
|
.next()
|
||||||
.map(|e| Expression::from_pair(e.into_inner().next().unwrap()));
|
.map(|e| Expression::from_pair(e.into_inner().next().unwrap()));
|
||||||
|
|
||||||
ForInit::VarDecl {
|
(kind, name, init_expr)
|
||||||
kind,
|
|
||||||
name,
|
|
||||||
init: init_expr,
|
|
||||||
}
|
}
|
||||||
}
|
_ => unimplemented!(
|
||||||
_ => ForInit::Expr(Expression::from_pair(p)),
|
"For loop init parsing not implemented yet: {:?}",
|
||||||
});
|
p.as_rule()
|
||||||
|
),
|
||||||
|
})
|
||||||
|
.unwrap();
|
||||||
|
|
||||||
let condition = inner.next().map(Expression::from_pair);
|
let condition = inner.next().map(Expression::from_pair);
|
||||||
let update = inner.next().map(Expression::from_pair);
|
let update = inner.next().map(Expression::from_pair);
|
||||||
@@ -260,12 +262,20 @@ impl Statement {
|
|||||||
|
|
||||||
Statement::For {
|
Statement::For {
|
||||||
init,
|
init,
|
||||||
condition,
|
condition: None,
|
||||||
update,
|
update: None,
|
||||||
body: Box::new(body),
|
body: Box::new(body),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Rule::var_assign => {
|
||||||
|
let mut inner = pair.into_inner();
|
||||||
|
let target = Expression::from_pair(inner.next().unwrap());
|
||||||
|
let value = Expression::from_pair(inner.next().unwrap());
|
||||||
|
|
||||||
|
Statement::VarAssign { target, value }
|
||||||
|
}
|
||||||
|
|
||||||
_ => unimplemented!(
|
_ => unimplemented!(
|
||||||
"Statement parsing not implemented yet: {:?}",
|
"Statement parsing not implemented yet: {:?}",
|
||||||
pair.as_rule()
|
pair.as_rule()
|
||||||
|
|||||||
@@ -1,11 +1,13 @@
|
|||||||
function add(a: int, b: int): int {
|
function add(a: int, b: int): int {
|
||||||
let sum = 0;
|
let sum = 0;
|
||||||
|
|
||||||
|
for (let i = 0; i < 10; i = i + 1) {
|
||||||
if (i == 5) {
|
if (i == 5) {
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
sum = sum + i;
|
sum = sum + i;
|
||||||
|
}
|
||||||
|
|
||||||
if (sum > 20) {
|
if (sum > 20) {
|
||||||
return sum;
|
return sum;
|
||||||
|
|||||||
Reference in New Issue
Block a user