Type alias projections & substitution rules.

1. Substitution variance (sv) is a substitution composition of type alias argument variance (av)
and corresponding expanding type argument variance (ev):
sv =
  | av == ev -> av
  | av == INVARIANT -> ev
  | ev == INVARIANT -> av
  | else -> (variance conflict error; av)

2. Resulting variance (rv) is a type argument composition of sv and type parameter variance (pv):
rv =
  | sv == tv => INVARIANT
  | sv == INVARIANT => INVARIANT
  | tv == INVARIANT => sv
  | else -> (variance conflict error; sv)
This commit is contained in:
Dmitry Petrov
2016-11-21 11:47:16 +03:00
parent 427c6386a9
commit bab9cde280
9 changed files with 126 additions and 43 deletions
@@ -14,13 +14,13 @@ public final class A : Outer<kotlin.Double, kotlin.Short> {
public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean
public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int
public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String
public final fun x(): Outer<kotlin.Float, kotlin.Long>.Alias<kotlin.String> /* = kotlin.collections.Map<kotlin.String, out kotlin.Float> */
public final fun x(): Outer<kotlin.Float, kotlin.Long>.Alias<kotlin.String> /* = kotlin.collections.Map<kotlin.String, kotlin.Float> */
}
}
public final class Derived : Outer<kotlin.String, kotlin.Int> {
public constructor Derived()
public final fun baz(): Outer<kotlin.String, kotlin.Int>.Alias<kotlin.Char> /* = kotlin.collections.Map<kotlin.Char, out kotlin.String> */
public final fun baz(): Outer<kotlin.String, kotlin.Int>.Alias<kotlin.Char> /* = kotlin.collections.Map<kotlin.Char, kotlin.String> */
public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean
public final fun foo(): Outer<kotlin.String, kotlin.Int>.Inner<kotlin.Char>
public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int
@@ -18,7 +18,7 @@ public open class BaseDerived2</*0*/ X> : BaseDerived1<kotlin.String, X> {
public final class Derived : BaseDerived2<kotlin.Int> {
public constructor Derived()
public final fun baz(): Outer<kotlin.Int, kotlin.String>.Alias<kotlin.Char> /* = kotlin.collections.Map<kotlin.Char, out kotlin.Int> */
public final fun baz(): Outer<kotlin.Int, kotlin.String>.Alias<kotlin.Char> /* = kotlin.collections.Map<kotlin.Char, kotlin.Int> */
public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean
public final fun foo(): Outer<kotlin.Int, kotlin.String>.Inner<kotlin.Char>
public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int
@@ -13,8 +13,8 @@ public fun test10(/*0*/ x: TC<kotlin.Number, kotlin.collections.Collection<kotli
public fun test11(/*0*/ x: TC<kotlin.Number, kotlin.collections.List<kotlin.Int>> /* = TColl<kotlin.Number, kotlin.collections.List<kotlin.Int>> */): kotlin.Unit
public fun test12(/*0*/ x: TC<kotlin.Number, kotlin.collections.List<kotlin.Any>> /* = TColl<kotlin.Number, kotlin.collections.List<kotlin.Any>> */): kotlin.Unit
public fun test2(/*0*/ x: NA<kotlin.Any> /* = Num<kotlin.Any> */): kotlin.Unit
public fun test3(/*0*/ x: NL<kotlin.Int> /* = NumColl<kotlin.collections.List<out kotlin.Int>> */): kotlin.Unit
public fun test4(/*0*/ x: NL<kotlin.Any> /* = NumColl<kotlin.collections.List<out kotlin.Any>> */): kotlin.Unit
public fun test3(/*0*/ x: NL<kotlin.Int> /* = NumColl<kotlin.collections.List<kotlin.Int>> */): kotlin.Unit
public fun test4(/*0*/ x: NL<kotlin.Any> /* = NumColl<kotlin.collections.List<kotlin.Any>> */): kotlin.Unit
public fun test9(/*0*/ x: TC<kotlin.Number, kotlin.collections.Collection<kotlin.Number>> /* = TColl<kotlin.Number, kotlin.collections.Collection<kotlin.Number>> */): kotlin.Unit
public final class Num</*0*/ T : kotlin.Number> {
+3 -3
View File
@@ -32,21 +32,21 @@ public final class Test2</*0*/ out S> : A2<kotlin.Any, S> /* = I1<S> */ {
public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String
}
public final class Test3</*0*/ out S> : AOut<S> /* = Out<out S> */ {
public final class Test3</*0*/ out S> : AOut<S> /* = Out<S> */ {
public constructor Test3</*0*/ out S>()
public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean
public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int
public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String
}
public final class Test4</*0*/ out S> : AInvOut<S, S> /* = InvOut<S, out S> */ {
public final class Test4</*0*/ out S> : AInvOut<S, S> /* = InvOut<S, S> */ {
public constructor Test4</*0*/ out S>()
public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean
public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int
public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String
}
public final class Test5</*0*/ out S> : AInvOutTT<S> /* = InvOut<S, out S> */ {
public final class Test5</*0*/ out S> : AInvOutTT<S> /* = InvOut<S, S> */ {
public constructor Test5</*0*/ out S>()
public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean
public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int
+3 -3
View File
@@ -12,19 +12,19 @@ public interface Out</*0*/ out R> {
public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String
}
public interface Q1</*0*/ out S> : Out<A1<S> /* = Out<Out<out S>> */> {
public interface Q1</*0*/ out S> : Out<A1<S> /* = Out<Out<S>> */> {
public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean
public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int
public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String
}
public interface Q2</*0*/ out S> : Out<A2<S> /* = Out<Out<out S>> */> {
public interface Q2</*0*/ out S> : Out<A2<S> /* = Out<Out<S>> */> {
public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean
public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int
public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String
}
public interface Q3</*0*/ out S> : Out<A3<S> /* = Inv<Out<out S>> */> {
public interface Q3</*0*/ out S> : Out<A3<S> /* = Inv<Out<S>> */> {
public open override /*1*/ /*fake_override*/ fun equals(/*0*/ other: kotlin.Any?): kotlin.Boolean
public open override /*1*/ /*fake_override*/ fun hashCode(): kotlin.Int
public open override /*1*/ /*fake_override*/ fun toString(): kotlin.String
@@ -3,6 +3,6 @@ package
public fun bar1(/*0*/ a: Array2D<kotlin.Int> /* = kotlin.Array<kotlin.Array<kotlin.Int>> */): Array2D<out kotlin.Number> /* = kotlin.Array<kotlin.Array<out kotlin.Number>> */
public fun bar2(/*0*/ m: TMap<*> /* = kotlin.collections.Map<*, *> */): [ERROR : Error function type]
public fun foo1(/*0*/ a: Array2D<out kotlin.Number> /* = kotlin.Array<kotlin.Array<out kotlin.Number>> */): Array2D<out kotlin.Number> /* = kotlin.Array<kotlin.Array<out kotlin.Number>> */
public fun </*0*/ T> foo2(/*0*/ m: TMap<T> /* = kotlin.collections.Map<T, out T> */): TMap<T> /* = kotlin.collections.Map<T, out T> */
public fun </*0*/ T> foo2(/*0*/ m: TMap<T> /* = kotlin.collections.Map<T, T> */): TMap<T> /* = kotlin.collections.Map<T, T> */
public typealias Array2D</*0*/ T> = kotlin.Array<kotlin.Array<T>>
public typealias TMap</*0*/ T> = kotlin.collections.Map<T, T>
@@ -18,3 +18,48 @@ typealias Inv3<T> = Inv<out T>
typealias Inv4<<!UNUSED_TYPEALIAS_PARAMETER!>T<!>> = Inv<*>
val inv1: Inv1<Int> = Inv<Int>()
fun inInv_Inv(x: In1<Int>) = x
fun inInv_In(x: In1<in Int>) = x
fun inInv_Out(x: <!CONFLICTING_PROJECTION_IN_TYPEALIAS_EXPANSION!>In1<out Int><!>) = x
fun inInv_Star(x: In1<*>) = x
fun inIn_Inv(x: In2<Int>) = x
fun inIn_In(x: In2<in Int>) = x
fun inIn_Out(x: <!CONFLICTING_PROJECTION_IN_TYPEALIAS_EXPANSION, CONFLICTING_PROJECTION_IN_TYPEALIAS_EXPANSION!>In2<out Int><!>) = x
fun inIn_Star(x: In2<*>) = x
fun inOut_Inv(x: <!CONFLICTING_PROJECTION_IN_TYPEALIAS_EXPANSION!>In3<Int><!>) = x
fun inOut_In(x: <!CONFLICTING_PROJECTION_IN_TYPEALIAS_EXPANSION!>In3<in Int><!>) = x
fun inOut_Out(x: <!CONFLICTING_PROJECTION_IN_TYPEALIAS_EXPANSION!>In3<out Int><!>) = x
fun inOut_Star(x: In3<*>) = x
fun outInv_Inv(x: Out1<Int>) = x
fun outInv_In(x: <!CONFLICTING_PROJECTION_IN_TYPEALIAS_EXPANSION!>Out1<in Int><!>) = x
fun outInv_Out(x: Out1<out Int>) = x
fun outInv_Star(x: Out1<*>) = x
fun outIn_Inv(x: <!CONFLICTING_PROJECTION_IN_TYPEALIAS_EXPANSION!>Out2<Int><!>) = x
fun outIn_In(x: <!CONFLICTING_PROJECTION_IN_TYPEALIAS_EXPANSION!>Out2<in Int><!>) = x
fun outIn_Out(x: <!CONFLICTING_PROJECTION_IN_TYPEALIAS_EXPANSION!>Out2<out Int><!>) = x
fun outIn_Star(x: Out2<*>) = x
fun outOut_Inv(x: Out3<Int>) = x
fun outOut_In(x: <!CONFLICTING_PROJECTION_IN_TYPEALIAS_EXPANSION, CONFLICTING_PROJECTION_IN_TYPEALIAS_EXPANSION!>Out3<in Int><!>) = x
fun outOut_Out(x: Out3<out Int>) = x
fun outOut_Star(x: Out3<*>) = x
fun invInv_Inv(x: Inv1<Int>) = x
fun invInv_In(x: Inv1<in Int>) = x
fun invInv_Out(x: Inv1<out Int>) = x
fun invInv_Star(x: Inv1<*>) = x
fun invIn_Inv(x: Inv2<Int>) = x
fun invIn_In(x: Inv2<in Int>) = x
fun invIn_Out(x: <!CONFLICTING_PROJECTION_IN_TYPEALIAS_EXPANSION!>Inv2<out Int><!>) = x
fun invIn_Star(x: Inv2<*>) = x
fun invOut_Inv(x: Inv3<Int>) = x
fun invOut_In(x: <!CONFLICTING_PROJECTION_IN_TYPEALIAS_EXPANSION!>Inv3<in Int><!>) = x
fun invOut_Out(x: Inv3<out Int>) = x
fun invOut_Star(x: Inv3<*>) = x
@@ -1,6 +1,42 @@
package
public val inv1: Inv1<kotlin.Int> /* = Inv<kotlin.Int> */
public fun inIn_In(/*0*/ x: In2<in kotlin.Int> /* = In<kotlin.Int> */): In2<in kotlin.Int> /* = In<kotlin.Int> */
public fun inIn_Inv(/*0*/ x: In2<kotlin.Int> /* = In<kotlin.Int> */): In2<kotlin.Int> /* = In<kotlin.Int> */
public fun inIn_Out(/*0*/ x: In2<out kotlin.Int> /* = In<out kotlin.Int> */): In2<out kotlin.Int> /* = In<out kotlin.Int> */
public fun inIn_Star(/*0*/ x: In2<*> /* = In<*> */): In2<*> /* = In<*> */
public fun inInv_In(/*0*/ x: In1<in kotlin.Int> /* = In<kotlin.Int> */): In1<in kotlin.Int> /* = In<kotlin.Int> */
public fun inInv_Inv(/*0*/ x: In1<kotlin.Int> /* = In<kotlin.Int> */): In1<kotlin.Int> /* = In<kotlin.Int> */
public fun inInv_Out(/*0*/ x: In1<out kotlin.Int> /* = In<out kotlin.Int> */): In1<out kotlin.Int> /* = In<out kotlin.Int> */
public fun inInv_Star(/*0*/ x: In1<*> /* = In<*> */): In1<*> /* = In<*> */
public fun inOut_In(/*0*/ x: In3<in kotlin.Int> /* = In<kotlin.Int> */): In3<in kotlin.Int> /* = In<kotlin.Int> */
public fun inOut_Inv(/*0*/ x: In3<kotlin.Int> /* = In<out kotlin.Int> */): In3<kotlin.Int> /* = In<out kotlin.Int> */
public fun inOut_Out(/*0*/ x: In3<out kotlin.Int> /* = In<out kotlin.Int> */): In3<out kotlin.Int> /* = In<out kotlin.Int> */
public fun inOut_Star(/*0*/ x: In3<*> /* = In<*> */): In3<*> /* = In<*> */
public fun invIn_In(/*0*/ x: Inv2<in kotlin.Int> /* = Inv<in kotlin.Int> */): Inv2<in kotlin.Int> /* = Inv<in kotlin.Int> */
public fun invIn_Inv(/*0*/ x: Inv2<kotlin.Int> /* = Inv<in kotlin.Int> */): Inv2<kotlin.Int> /* = Inv<in kotlin.Int> */
public fun invIn_Out(/*0*/ x: Inv2<out kotlin.Int> /* = Inv<out kotlin.Int> */): Inv2<out kotlin.Int> /* = Inv<out kotlin.Int> */
public fun invIn_Star(/*0*/ x: Inv2<*> /* = Inv<*> */): Inv2<*> /* = Inv<*> */
public fun invInv_In(/*0*/ x: Inv1<in kotlin.Int> /* = Inv<in kotlin.Int> */): Inv1<in kotlin.Int> /* = Inv<in kotlin.Int> */
public fun invInv_Inv(/*0*/ x: Inv1<kotlin.Int> /* = Inv<kotlin.Int> */): Inv1<kotlin.Int> /* = Inv<kotlin.Int> */
public fun invInv_Out(/*0*/ x: Inv1<out kotlin.Int> /* = Inv<out kotlin.Int> */): Inv1<out kotlin.Int> /* = Inv<out kotlin.Int> */
public fun invInv_Star(/*0*/ x: Inv1<*> /* = Inv<*> */): Inv1<*> /* = Inv<*> */
public fun invOut_In(/*0*/ x: Inv3<in kotlin.Int> /* = Inv<in kotlin.Int> */): Inv3<in kotlin.Int> /* = Inv<in kotlin.Int> */
public fun invOut_Inv(/*0*/ x: Inv3<kotlin.Int> /* = Inv<out kotlin.Int> */): Inv3<kotlin.Int> /* = Inv<out kotlin.Int> */
public fun invOut_Out(/*0*/ x: Inv3<out kotlin.Int> /* = Inv<out kotlin.Int> */): Inv3<out kotlin.Int> /* = Inv<out kotlin.Int> */
public fun invOut_Star(/*0*/ x: Inv3<*> /* = Inv<*> */): Inv3<*> /* = Inv<*> */
public fun outIn_In(/*0*/ x: Out2<in kotlin.Int> /* = Out<in kotlin.Int> */): Out2<in kotlin.Int> /* = Out<in kotlin.Int> */
public fun outIn_Inv(/*0*/ x: Out2<kotlin.Int> /* = Out<in kotlin.Int> */): Out2<kotlin.Int> /* = Out<in kotlin.Int> */
public fun outIn_Out(/*0*/ x: Out2<out kotlin.Int> /* = Out<kotlin.Int> */): Out2<out kotlin.Int> /* = Out<kotlin.Int> */
public fun outIn_Star(/*0*/ x: Out2<*> /* = Out<*> */): Out2<*> /* = Out<*> */
public fun outInv_In(/*0*/ x: Out1<in kotlin.Int> /* = Out<in kotlin.Int> */): Out1<in kotlin.Int> /* = Out<in kotlin.Int> */
public fun outInv_Inv(/*0*/ x: Out1<kotlin.Int> /* = Out<kotlin.Int> */): Out1<kotlin.Int> /* = Out<kotlin.Int> */
public fun outInv_Out(/*0*/ x: Out1<out kotlin.Int> /* = Out<kotlin.Int> */): Out1<out kotlin.Int> /* = Out<kotlin.Int> */
public fun outInv_Star(/*0*/ x: Out1<*> /* = Out<*> */): Out1<*> /* = Out<*> */
public fun outOut_In(/*0*/ x: Out3<in kotlin.Int> /* = Out<in kotlin.Int> */): Out3<in kotlin.Int> /* = Out<in kotlin.Int> */
public fun outOut_Inv(/*0*/ x: Out3<kotlin.Int> /* = Out<kotlin.Int> */): Out3<kotlin.Int> /* = Out<kotlin.Int> */
public fun outOut_Out(/*0*/ x: Out3<out kotlin.Int> /* = Out<kotlin.Int> */): Out3<out kotlin.Int> /* = Out<kotlin.Int> */
public fun outOut_Star(/*0*/ x: Out3<*> /* = Out<*> */): Out3<*> /* = Out<*> */
public final class In</*0*/ in T> {
public constructor In</*0*/ in T>()