aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorBruce Hill <bruce@bruce-hill.com>2025-04-06 15:09:44 -0400
committerBruce Hill <bruce@bruce-hill.com>2025-04-06 15:09:44 -0400
commit448e805293989b06e07878a4a87fdd378f7c6e02 (patch)
treed0364efbeaad0eeb863593c26745d64deaf4a212
parent4043a99e0df9fab6791c485721c0046971754175 (diff)
Re-implement multiple patterns for `when` blocks
-rw-r--r--src/parse.c14
-rw-r--r--test/enums.tm12
-rw-r--r--test/when.tm19
3 files changed, 34 insertions, 11 deletions
diff --git a/src/parse.c b/src/parse.c
index a11fc971..0f76243d 100644
--- a/src/parse.c
+++ b/src/parse.c
@@ -996,11 +996,17 @@ PARSER(parse_when) {
spaces(&pos);
ast_t *pattern = expect(ctx, start, &pos, parse_expr, "I expected a pattern to match here");
spaces(&pos);
- tmp = pos;
- if (!match(&tmp, ":"))
- parser_err(ctx, tmp, tmp, "I expected a colon ':' after this clause");
+ when_clause_t *new_clauses = new(when_clause_t, .pattern=pattern, .next=clauses);
+ while (match(&pos, ",")) {
+ pattern = expect(ctx, start, &pos, parse_expr, "I expected a pattern to match here");
+ new_clauses = new(when_clause_t, .pattern=pattern, .next=new_clauses);
+ spaces(&pos);
+ }
ast_t *body = expect(ctx, start, &pos, parse_block, "I expected a body for this 'when' clause");
- clauses = new(when_clause_t, .pattern=pattern, .body=body, .next=clauses);
+ for (when_clause_t *c = new_clauses; c && c != clauses; c = c->next) {
+ c->body = body;
+ }
+ clauses = new_clauses;
tmp = pos;
whitespace(&tmp);
}
diff --git a/test/enums.tm b/test/enums.tm
index 19590353..a11f95f9 100644
--- a/test/enums.tm
+++ b/test/enums.tm
@@ -66,6 +66,18 @@ func main():
while when cases[i] is One(x):
>> x
i += 1
+
+ >> [
+ (
+ when x is One(y), Two(y,_):
+ "Small $y"
+ is Zero:
+ "Zero"
+ else:
+ "Other"
+ ) for x in [Foo.Zero, Foo.One(1), Foo.Two(2,2), Foo.Three(3,"",no)]
+ ]
+ = ["Zero", "Small 1", "Small 2", "Other"]
>> expr := when cases[1] is One(y):
y + 1
diff --git a/test/when.tm b/test/when.tm
index 77c97af5..d93745dd 100644
--- a/test/when.tm
+++ b/test/when.tm
@@ -1,13 +1,18 @@
# Tests for the 'when' block
func main():
- str := "B"
- when str is "A":
- fail("First")
- is "B":
- say("Success")
- is "C":
- fail("Third")
+ answers := [
+ (
+ when x is "A","B":
+ "A or B"
+ is "C":
+ "C"
+ else:
+ "Other"
+ ) for x in ["A", "B", "C", "D"]
+ ]
+ >> answers
+ = ["A or B", "A or B", "C", "Other"]
n := 23
>> when n is 1: Int64(1)