Skip to content

Commit 502cf42

Browse files
fcouryclaude
andcommitted
feat: add support for else-if chains
- Update parser to handle 'else if' syntax - Allow chaining multiple else-if conditions - Convert else-if to nested if statements in else block - Add comprehensive tests for else-if functionality - All tests pass including transpiler support 🤖 Generated with [Claude Code](https://claude.ai/code) Co-Authored-By: Claude <[email protected]>
1 parent 6c45ca0 commit 502cf42

File tree

11 files changed

+78
-13
lines changed

11 files changed

+78
-13
lines changed

src/parser.rs

Lines changed: 20 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -1818,24 +1818,31 @@ impl Parser {
18181818
if self.current_token().kind == TokenKind::Else {
18191819
self.advance(); // Consume 'else'
18201820

1821-
if self.current_token().kind != TokenKind::LBrace {
1822-
return Err(Error::new_parse(
1823-
"Expected '{' after else".to_string(),
1824-
self.current_token().span,
1825-
));
1826-
}
1827-
1828-
self.advance(); // Consume '{'
1829-
else_block = self.parse_block()?;
1821+
// Check if this is an 'else if'
1822+
if self.current_token().kind == TokenKind::If {
1823+
// Parse the if expression as a single statement in the else block
1824+
let else_if_expr = self.parse_if_expression()?;
1825+
end_span = else_if_expr.span().end;
1826+
else_block = vec![Stmt::Expression(else_if_expr, false)];
1827+
} else if self.current_token().kind == TokenKind::LBrace {
1828+
// Regular else block
1829+
self.advance(); // Consume '{'
1830+
else_block = self.parse_block()?;
18301831

1831-
if self.current_token().kind != TokenKind::RBrace {
1832+
if self.current_token().kind != TokenKind::RBrace {
1833+
return Err(Error::new_parse(
1834+
"Expected '}' after else block".to_string(),
1835+
self.current_token().span,
1836+
));
1837+
}
1838+
end_span = self.current_token().span.end;
1839+
self.advance(); // Consume '}'
1840+
} else {
18321841
return Err(Error::new_parse(
1833-
"Expected '}' after else block".to_string(),
1842+
"Expected '{' or 'if' after else".to_string(),
18341843
self.current_token().span,
18351844
));
18361845
}
1837-
end_span = self.current_token().span.end;
1838-
self.advance(); // Consume '}'
18391846
}
18401847

18411848
Ok(Expr::If(

tests/scripts/else-if-complex.hk

Lines changed: 44 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,44 @@
1+
// Test multiple else-if chains
2+
let score = 85;
3+
4+
if score >= 90 {
5+
println!("Grade: A");
6+
} else if score >= 80 {
7+
println!("Grade: B");
8+
} else if score >= 70 {
9+
println!("Grade: C");
10+
} else if score >= 60 {
11+
println!("Grade: D");
12+
} else {
13+
println!("Grade: F");
14+
}
15+
16+
// Test else-if without final else
17+
let temp = 25;
18+
if temp < 0 {
19+
println!("Freezing");
20+
} else if temp < 10 {
21+
println!("Cold");
22+
} else if temp < 20 {
23+
println!("Cool");
24+
} else if temp < 30 {
25+
println!("Warm");
26+
}
27+
28+
// Test nested else-if in else-if
29+
let x = 15;
30+
let y = 20;
31+
32+
if x > 20 {
33+
println!("x > 20");
34+
} else if x > 10 {
35+
if y > 25 {
36+
println!("x > 10 and y > 25");
37+
} else if y > 15 {
38+
println!("x > 10 and y > 15");
39+
} else {
40+
println!("x > 10 and y <= 15");
41+
}
42+
} else {
43+
println!("x <= 10");
44+
}

tests/scripts/else-if-complex.hk.err

Whitespace-only changes.
Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
Grade: B
2+
Warm
3+
x > 10 and y > 15

tests/scripts/else-if-complex.hk.tr.err

Whitespace-only changes.
Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
Grade: B
2+
Warm
3+
x > 10 and y > 15

tests/scripts/else-if.hk

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,6 @@
1+
let a = 1;
2+
if a == 2 {
3+
println!("a is 2");
4+
} else if a == 1 {
5+
println!("a is 1");
6+
}

tests/scripts/else-if.hk.err

Whitespace-only changes.

tests/scripts/else-if.hk.out

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
a is 1

tests/scripts/else-if.hk.tr.err

Whitespace-only changes.

0 commit comments

Comments
 (0)