Skip to content

Commit a39e5b2

Browse files
committed
Lower precedence of qualified types' with
1 parent 9997371 commit a39e5b2

File tree

2 files changed

+40
-21
lines changed

2 files changed

+40
-21
lines changed

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

Lines changed: 34 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -1636,6 +1636,7 @@ object Parsers {
16361636
* | TypTypeParamClause ‘=>>’ Type
16371637
* | FunParamClause ‘=>>’ Type
16381638
* | MatchType
1639+
* | QualifiedType2 -- under qualifiedTypes
16391640
* | InfixType
16401641
* FunType ::= (MonoFunType | PolyFunType)
16411642
* MonoFunType ::= FunTypeArgs (‘=>’ | ‘?=>’) Type
@@ -1646,6 +1647,11 @@ object Parsers {
16461647
* | `(' [ FunArgType {`,' FunArgType } ] `)'
16471648
* | '(' [ TypedFunParam {',' TypedFunParam } ')'
16481649
* MatchType ::= InfixType `match` <<< TypeCaseClauses >>>
1650+
* QualifiedType2 ::= InfixType `with` PostfixExprf
1651+
* IntoType ::= [‘into’] IntoTargetType
1652+
* | ‘( IntoType ‘)’
1653+
* IntoTargetType ::= Type
1654+
* | FunTypeArgs (‘=>’ | ‘?=>’) IntoType
16491655
*/
16501656
def typ(inContextBound: Boolean = false): Tree =
16511657
val start = in.offset
@@ -1705,6 +1711,8 @@ object Parsers {
17051711
functionRest(t :: Nil)
17061712
case MATCH =>
17071713
matchType(t)
1714+
case WITH if in.featureEnabled(Feature.qualifiedTypes) =>
1715+
qualifiedTypeShort(t)
17081716
case FORSOME =>
17091717
syntaxError(ExistentialTypesNoLongerSupported())
17101718
t
@@ -1839,6 +1847,7 @@ object Parsers {
18391847
def funParamClauses(): List[List[ValDef]] =
18401848
if in.token == LPAREN then funParamClause() :: funParamClauses() else Nil
18411849

1850+
18421851
/** InfixType ::= RefinedType {id [nl] RefinedType}
18431852
* | RefinedType `^` -- under captureChecking
18441853
*/
@@ -1893,22 +1902,12 @@ object Parsers {
18931902
t
18941903
}
18951904

1896-
/** With qualifiedTypes enabled:
1897-
* WithType ::= AnnotType [`with' PostfixExpr]
1898-
*
1899-
* Otherwise:
1900-
* WithType ::= AnnotType {`with' AnnotType} (deprecated)
1901-
*/
1905+
/** WithType ::= AnnotType {`with' AnnotType} (deprecated)
1906+
*/
19021907
def withType(): Tree = withTypeRest(annotType())
19031908

19041909
def withTypeRest(t: Tree): Tree =
1905-
if in.featureEnabled(Feature.qualifiedTypes) && in.token == WITH then
1906-
if inQualifiedType then t
1907-
else
1908-
in.nextToken()
1909-
val qualifier = postfixExpr()
1910-
QualifiedTypeTree(t, None, qualifier).withSpan(Span(t.span.start, qualifier.span.end))
1911-
else if in.token == WITH then
1910+
if in.token == WITH && !in.featureEnabled(Feature.qualifiedTypes) then
19121911
val withOffset = in.offset
19131912
in.nextToken()
19141913
if in.token == LBRACE || in.token == INDENT then
@@ -2247,6 +2246,17 @@ object Parsers {
22472246
accept(RBRACE)
22482247
QualifiedTypeTree(tp, Some(id), qualifier).withSpan(Span(startOffset, qualifier.span.end))
22492248

2249+
/** `with` PostfixExpr
2250+
*/
2251+
def qualifiedTypeShort(t: Tree): Tree =
2252+
if inQualifiedType then
2253+
t
2254+
else
2255+
accept(WITH)
2256+
val qualifier = postfixExpr()
2257+
QualifiedTypeTree(t, None, qualifier).withSpan(Span(t.span.start, qualifier.span.end))
2258+
2259+
22502260
/** TypeBounds ::= [`>:' TypeBound ] [`<:' TypeBound ]
22512261
* TypeBound ::= Type
22522262
* | CaptureSet -- under captureChecking
@@ -2323,7 +2333,12 @@ object Parsers {
23232333

23242334
def typeDependingOn(location: Location): Tree =
23252335
if location.inParens then typ()
2326-
else if location.inPattern then rejectWildcardType(refinedType())
2336+
else if location.inPattern then
2337+
val t = rejectWildcardType(refinedType())
2338+
if in.featureEnabled(Feature.qualifiedTypes) && in.token == WITH then
2339+
qualifiedTypeShort(t)
2340+
else
2341+
t
23272342
else infixType()
23282343

23292344
/* ----------- EXPRESSIONS ------------------------------------------------ */
@@ -3165,10 +3180,11 @@ object Parsers {
31653180
if (isIdent(nme.raw.BAR)) { in.nextToken(); pattern1(location) :: patternAlts(location) }
31663181
else Nil
31673182

3168-
/** Pattern1 ::= PatVar `:` RefinedType
3169-
* | [‘-’] integerLiteral `:` RefinedType
3170-
* | [‘-’] floatingPointLiteral `:` RefinedType
3171-
* | Pattern2
3183+
/** Pattern1 ::= PatVar `:` QualifiedType3
3184+
* | [‘-’] integerLiteral `:` QualifiedType3
3185+
* | [‘-’] floatingPointLiteral `:` QualifiedType3
3186+
* | Pattern2
3187+
* QualifiedType3 ::= RefinedType [`with` PostfixExpr]
31723188
*/
31733189
def pattern1(location: Location = Location.InPattern): Tree =
31743190
val p = pattern2(location)

tests/printing/qualified-types.check

Lines changed: 6 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -60,10 +60,13 @@ package example {
6060
Int @qualified[Int]((x3: Int) => x3 < 10)
6161
= ???
6262
val x4:
63-
Int @qualified[Int]((x4: Int) => x4 > 0) &
64-
Int @qualified[Int]((x4: Int) => x4 < 10)
63+
(Int @qualified[Int]((x4: Int) => x4 > 0) & Int) @qualified[
64+
Int @qualified[Int]((x4: Int) => x4 > 0) & Int]((
65+
x4: Int @qualified[Int]((x4: Int) => x4 > 0) & Int) => x4 < 10)
6566
= ???
66-
val x5: Int & String @qualified[String]((x5: String) => false) = ???
67+
val x5:
68+
(Int & String) @qualified[Int & String]((x5: Int & String) => false)
69+
= ???
6770
val x6:
6871
(Int @qualified[Int]((x6: Int) => x6 > 0) & Int) @qualified[
6972
Int @qualified[Int]((x6: Int) => x6 > 0) & Int]((

0 commit comments

Comments
 (0)