You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
Copy file name to clipboardExpand all lines: docs/docs/reference/other-new-features/quoted-pattern-spec.md
+83-46Lines changed: 83 additions & 46 deletions
Original file line number
Diff line number
Diff line change
@@ -4,74 +4,111 @@ title: "Pattern Matching on Quoted Code"
4
4
---
5
5
6
6
7
-
8
7
## Overview
9
8
9
+
Any top level quote `'{ ... }` in a pattern position will become a quoted pattern. Inside quoteted pattern parts of the code can be spliced with `$` which extracts that part of the code.
10
+
Splices ca be of two forms:
11
+
* A splice `${ ... : Expr[T] }` that can be places in any expression position.
12
+
* A splice `${ ... : Bind[T] }` that can be placed on names of `val`s, `var`s or `def`s
13
+
10
14
```scala
11
15
deffoo(x: Expr[Int]) giventasty.Reflect:Expr[Int] = x match {
12
-
case'{ val$a= $x; (${Bind(`a`)}:Int) +($y: Int) } =>'{ $x +$y } // TODO needs fix for #6328, `a` is currently not in scope while typing
16
+
case'{ val$a:Int= $x; (${Bind(`a`)}:Int) +1} =>'{ $x +1 } // TODO needs fix for #6328, `a` is currently not in scope while typing
13
17
}
14
18
```
19
+
In the example above we have `$a` which provides a `Bind[Int]`, `$x` which provides an `Expr[Int]` and `${Bind(`a`)}` which probides an `Expr[Int]` that is pattern matched against `Bind(`a`)` to check that it is a reference to `a`.
20
+
21
+
Quoted patterns are transformed urring typer to a call of `scala.internal.quoted.Matcher.unapply` which splits the quoted code into the patterns and a reifiable quote that will be used as whitness at runtime.
15
22
16
23
```scala
17
24
deffoo(x: Expr[Int]) giventasty.Reflect:Expr[Int] = x match {
The `scrutineeExpr` is a normal quoted expression while `patternExpr` may contain holes representing splices.
38
+
The `scrutineeExpr` is a normal quoted expression while `patternExpr` may contain holes representing splices.
32
39
The result of pattern matching is `None` if the expressions are not equivalent, otherwise it returns `Some` (some tuple) containing the contents of the matched holes.
33
40
41
+
Let's define some abstractions on the possible results of this pattern matching using the alias `Matching`:
defmatches(scrutinee: Tree, pattern: Tree) givenEnv:Matching// described by cases in the tables bellow
53
+
54
+
defenvWith(equiv: (Symbol, Symbol)*) givenEnv:Env// Adds to the current environment the fact that s1 from the scrutinee is equivalent to s2 in the pattern
| `val a: A = b`<br>`lazy val a: A = b`<br>`var a: A = b` | `val x: X = y`<br>`lazy val x: X = y`<br>`var x: X = y` | `matches('[A], '[X]) ++ matches('b, 'y) given envWith(a.sym -> b.sym)`
0 commit comments