Skip to content

Commit 7f5a368

Browse files
committed
Allow <pattern> : <type> syntax
So far, the pattern in a type ascription had to be a variable. But there are use cases where we want to have a general pattern in this position.
1 parent 4d715ce commit 7f5a368

File tree

5 files changed

+23
-12
lines changed

5 files changed

+23
-12
lines changed

compiler/src/dotty/tools/dotc/parsing/Parsers.scala

Lines changed: 2 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1925,12 +1925,11 @@ object Parsers {
19251925
if (isIdent(nme.raw.BAR)) { in.nextToken(); pattern1() :: patternAlts() }
19261926
else Nil
19271927

1928-
/** Pattern1 ::= PatVar Ascription
1929-
* | Pattern2
1928+
/** Pattern1 ::= Pattern2 [Ascription]
19301929
*/
19311930
def pattern1(): Tree = {
19321931
val p = pattern2()
1933-
if (isVarPattern(p) && in.token == COLON) {
1932+
if (in.token == COLON) {
19341933
in.nextToken()
19351934
ascription(p, Location.InPattern)
19361935
}

compiler/src/dotty/tools/dotc/transform/patmat/Space.scala

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -339,10 +339,10 @@ class SpaceEngine(implicit ctx: Context) extends SpaceLogic {
339339
}
340340
else
341341
Prod(erase(pat.tpe.stripAnnots), erase(fun.tpe), fun.symbol, pats.map(project), isIrrefutableUnapply(fun))
342-
case Typed(pat: UnApply, _) =>
343-
project(pat)
344-
case Typed(expr, tpt) =>
342+
case Typed(expr @ Ident(nme.WILDCARD), tpt) =>
345343
Typ(erase(expr.tpe.stripAnnots), true)
344+
case Typed(pat, _) =>
345+
project(pat)
346346
case This(_) =>
347347
Typ(pat.tpe.stripAnnots, false)
348348
case EmptyTree => // default rethrow clause of try/catch, check tests/patmat/try2.scala

docs/docs/internals/syntax.md

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -261,8 +261,7 @@ TypeCaseClauses ::= TypeCaseClause { TypeCaseClause }
261261
TypeCaseClause ::= ‘case’ InfixType ‘=>’ Type [nl]
262262
263263
Pattern ::= Pattern1 { ‘|’ Pattern1 } Alternative(pats)
264-
Pattern1 ::= PatVar ‘:’ RefinedType Bind(name, Typed(Ident(wildcard), tpe))
265-
| Pattern2
264+
Pattern1 ::= Pattern2 [‘:’ RefinedType] Bind(name, Typed(Ident(wildcard), tpe))
266265
Pattern2 ::= [id ‘@’] InfixPattern Bind(name, pat)
267266
InfixPattern ::= SimplePattern { id [nl] SimplePattern } InfixOp(pat, op, pat)
268267
SimplePattern ::= PatVar Ident(wildcard)

tests/pos/patmat.scala

Lines changed: 7 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -8,15 +8,15 @@ object Test {
88

99
xs.length match {
1010
case 0 => println("0")
11-
case 1 => println("1")
11+
case 1: Int => println("1")
1212
case 2 => println("2")
1313
case 3 => println("3")
1414
case 4 => println("4")
1515
case _ => println("something else")
1616
}
1717

1818
(xs.length, xs) match {
19-
case (0, Nil) => println("1")
19+
case (0, Nil: List[Int]) => println("1")
2020
case (_, Nil) => println("2")
2121
case (0, _) => println("3")
2222
case (x, y) => println("4")
@@ -46,4 +46,9 @@ object Test {
4646
case Some(s) => println(s)
4747
case None => println("nothing")
4848
}
49+
50+
type IntPair = (Int, Int)
51+
??? match {
52+
case (x, y): IntPair => x * y
53+
}
4954
}

tests/run/genericNumLits.scala

Lines changed: 10 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -32,18 +32,26 @@ object Test extends App {
3232
x match {
3333
case 13232202002020202020202 => ()
3434
}
35+
(x: Any) match {
36+
case 13232202002020202020202: BigInt => ()
37+
}
3538
y match {
3639
case 13232202002020202020202 => assert(false)
3740
case -0xaabb12345ACF12345AC => ()
3841
}
3942
z match {
4043
case 132322020020.223 => ()
4144
}
42-
z match {
43-
case 132322020020.223 => ()
45+
(z: Any) match {
46+
case 132322020020.223: BigDecimal => ()
4447
}
4548

4649
e match {
4750
case 1234 =>
4851
}
52+
(e: Any) match {
53+
case 12: Even => assert(false)
54+
case 1234: Even =>
55+
case _: Even =>
56+
}
4957
}

0 commit comments

Comments
 (0)