also looking at this
fix(interpreter): match range and or patterns in match statements
#930
2 files
+90
-0
| @@ -12392,6 +12392,30 @@ pub const Interpreter = struct { | ||
| 12392 | 12392 | |
| 12393 | 12393 | return true; |
| 12394 | 12394 | }, |
| 12395 | .Range => |range_pattern| { | |
| 12396 | // Range pattern: start..end (exclusive) or start..=end (inclusive) | |
| 12397 | if (value != .Int) return false; | |
| 12398 | const start = try self.evaluateExpression(range_pattern.start, env); | |
| 12399 | const end = try self.evaluateExpression(range_pattern.end, env); | |
| 12400 | if (start != .Int or end != .Int) return false; | |
| 12401 | if (value.Int < start.Int) return false; | |
| 12402 | return if (range_pattern.inclusive) value.Int <= end.Int else value.Int < end.Int; | |
| 12403 | }, | |
| 12404 | .Or => |or_patterns| { | |
| 12405 | // Or pattern: matches if any alternative matches. Each | |
| 12406 | // alternative binds into a scratch scope so a failed one | |
| 12407 | // leaves no bindings behind; the winner's are copied to env. | |
| 12408 | for (or_patterns) |alt_pattern| { | |
| 12409 | var alt_env = Environment.init(self.arena.allocator(), env); | |
| 12410 | defer alt_env.deinit(); | |
| 12411 | if (try self.matchPatternNode(alt_pattern, value, &alt_env)) { | |
| 12412 | var it = alt_env.bindings.iterator(); | |
| 12413 | while (it.next()) |entry| try env.define(entry.key_ptr.*, entry.value_ptr.*); | |
| 12414 | return true; | |
| 12415 | } | |
| 12416 | } | |
| 12417 | return false; | |
| 12418 | }, | |
| 12395 | 12419 | else => { |
| 12396 | 12420 | // Other pattern types not yet implemented |
| 12397 | 12421 | return false; |