File tree Expand file tree Collapse file tree 3 files changed +80
-0
lines changed Expand file tree Collapse file tree 3 files changed +80
-0
lines changed Original file line number Diff line number Diff line change 1+ ---
2+ layout : doc-page
3+ title : " Type Lambdas - More Details"
4+ ---
5+
6+ ## Syntax
7+
8+ ```
9+ Type ::= ... | HkTypeParamClause ‘=>’ Type
10+ HkTypeParamClause ::= ‘[’ HkTypeParam {‘,’ HkTypeParam} ‘]’
11+ HkTypeParam ::= {Annotation} [‘+’ | ‘-’] (Id[HkTypeParamClause] | ‘_’) TypeBounds
12+ TypeBounds ::= [‘>:’ Type] [‘<:’ Type]
13+ ```
14+
15+ ### Type Checking
16+
17+ A type lambda such ` [X] => F[X] ` defines a function from types to types. The parameter(s) may carry bounds and variance annotations.
18+ If a parameter is is bounded, as in ` [X >: L <: H] => F[X] ` it is checked that arguments to the parameters conform to the bounds ` L ` and ` H ` .
19+ Only the upper bound ` H ` can be F-bounded, i.e. ` X ` can appear in it.
20+
21+ A variance annotation on a parameter indicates a subtyping relationship on type instances. For instance, given
22+ ```
23+ type TL1 = [+A] => F[A]
24+ type TL2 = [-A] => F[A]
25+ ```
26+ and two types ` S <: T ` , we have
27+ ```
28+ TL1[S] <: TL1[T
29+ TL2[T] <: TL2[S]
30+ ```
31+ It is checked that variance annotations on parameters of type lambdas are respected by the parameter occurrences on the
32+ type lambda's body.
33+
34+ ## Subtyping Rules
35+
36+ Assume two type lambdas
37+ ```
38+ type TL1 = [v1 X >: L1 <: U1] => R1
39+ type TL2 = [v2 X >: L2 <: U2] => R2
40+ ```
41+ where ` v1 ` and ` v2 ` are optional variance annotations: ` + ` , ` - ` , or absent.
42+ Then ` TL1 <: TL2 ` , if the type interval ` L2..U2 ` is contained in the type interval ` L1..U1 ` (i.e.
43+ ` L1 <: L2 ` and ` U2 <: U1 ` ), and either ` v2 ` is absent or ` v1 = v2 ` .
44+
45+
46+
47+
48+
49+
Original file line number Diff line number Diff line change @@ -20,3 +20,5 @@ is a shorthand for a plain type definition with a type-lambda as its
2020right-hand side:
2121
2222 type T = [X] => (X, X)
23+
24+ [ More details] ( ./type-lambdas-spec.md )
Original file line number Diff line number Diff line change 1+ object Test extends App {
2+
3+ trait Ord [X ]
4+
5+ type TL1 = [X <: Ord [X ]] => (X , X ) // OK
6+ type TL2 = [X >: Ord [X ]] => (X , X ) // error
7+
8+ class C extends Ord [C ]
9+
10+ type T1 = TL1 [Int ] // will be discovered later
11+ type T2 = TL1 [C ] // OK
12+
13+ class Ref [X ](init : X ) {
14+ var x : X = init
15+ }
16+
17+ type TL3 = [+ X ] => Ref [X ]
18+
19+ def f [F <: [+ X ] => Any ](x : F [String ]): F [Any ] = x
20+
21+ val sref = new Ref [String ](" abc" )
22+ val aref : Ref [Any ] = f[TL3 ](sref)
23+ aref.x = 1
24+ val s : String = sref.x
25+
26+
27+
28+
29+ }
You can’t perform that action at this time.
0 commit comments