@@ -434,11 +434,57 @@ Over half of the switch cases in a large corpus of packages contain either a
434
434
single return statement or an assignment followed by a break so there is some
435
435
evidence this will be useful.
436
436
437
- ** TODO: Something like an if statement that matches a single pattern and binds
438
- its variables in the then branch.**
437
+ ### If-case statement
439
438
440
- ** TODO: Something like a Swift guard-let that matches a single pattern and binds
441
- in the rest of the block or exits if the pattern does not match.**
439
+ Often you want to conditionally match and destructure some data, but you only
440
+ want to test a value against a single pattern. You can use a ` switch ` statement
441
+ for that, but it's pretty verbose:
442
+
443
+ ``` dart
444
+ switch (json) {
445
+ case [int x, int y]:
446
+ return Point(x, y);
447
+ }
448
+ ```
449
+
450
+ We can make simple uses like this a little cleaner by introducing an if-like
451
+ form similar to [ if-case in Swift] [ ] :
452
+
453
+ [ if-case in swift ] : https://useyourloaf.com/blog/swift-if-case-let/
454
+
455
+ ``` dart
456
+ if (case [int x, int y] = json) return Point(x, y);
457
+ ```
458
+
459
+ It may have an else branch as well:
460
+
461
+ ``` dart
462
+ if (case [int x, int y] = json) {
463
+ print('Was coordinate array $x,$y');
464
+ } else {
465
+ throw FormatException('Invalid JSON.');
466
+ }
467
+ ```
468
+
469
+ The grammar is:
470
+
471
+ ```
472
+ ifCaseStatement ::= 'if' '(' 'case' matcher '=' expression ')'
473
+ statement ('else' statement)?
474
+ ```
475
+
476
+ The ` expression ` is evaluated and matched against ` matcher ` . If the pattern
477
+ matches, then the then branch is executed with any variables the pattern
478
+ defines in scope. Otherwise, the else branch is executed if there is one.
479
+
480
+ Unlike ` switch ` , this form doesn't allow a guard clause. Guards are important in
481
+ switch cases because, unlike nesting an if statement * inside* the switch case, a
482
+ failed guard will continue to try later cases in the switch. That is less
483
+ important here since the only other case is the else branch.
484
+
485
+ ** TODO: Consider allowing guard clauses here. That probably necessitates
486
+ changing guard clauses to use a keyword other than ` if ` since ` if ` nested inside
487
+ an ` if ` condition looks pretty strange.**
442
488
443
489
### Irrefutable patterns ("binders")
444
490
@@ -865,8 +911,9 @@ arity of the type of `typeName`.
865
911
866
912
A pattern always appears in the context of some value expression that it is
867
913
being matched against. In a switch statement or expression, the value expression
868
- is the value being switched on. In a variable declaration, the value is the
869
- initializer:
914
+ is the value being switched on. In an if-case statement, the value is the result
915
+ of the expression to the right of the ` = ` . In a variable declaration, the value
916
+ is the initializer:
870
917
871
918
``` dart
872
919
var (a, b) = (1, 2);
@@ -1221,6 +1268,7 @@ that contains the pattern:
1221
1268
* **Switch statement case**: The guard clause and the statements of the
1222
1269
subsequent non-empty case body.
1223
1270
* **Switch expression case**: The guard clause and the case expression.
1271
+ * **If-case statement**: The then statement.
1224
1272
1225
1273
Multiple switch case patterns may share the same variable scope if their case
1226
1274
bodies are empty:
@@ -1371,6 +1419,15 @@ behavior.
1371
1419
expression after it and yield that as the result of the entire switch
1372
1420
expression.
1373
1421
1422
+ #### If-case statement
1423
+
1424
+ 1 . Evaluate the ` expression ` producing ` v ` .
1425
+
1426
+ 2 . Match the ` matcher ` pattern against ` v ` .
1427
+
1428
+ 3 . If the match succeeds, evaluate the then ` statement ` . Otherwise, if there
1429
+ is an ` else ` clause, evaluate the else ` statement ` .
1430
+
1374
1431
### Matching (refuting and destructuring)
1375
1432
1376
1433
At runtime, a pattern is matched against a value. This determines whether or not
@@ -1523,6 +1580,8 @@ main() {
1523
1580
- Add a shorthand for destructuring a named record field to a variable with
1524
1581
the same name.
1525
1582
1583
+ - Add if-case statement.
1584
+
1526
1585
### 1.1
1527
1586
1528
1587
- Copy editing and clean up.
0 commit comments