Type A is not assigned to type B with conditional typescript types 2.8

this is actually a sequel to typescript 2.8. Exclude: is it possible to reload a section type? - I am having problems introducing conditional types in my code.

Note that conditional types are new with typescript 2.8, so currently this should be built using typescript 2.8rc.

I reduced the current problem to this rather small test case:

export class Option<T> {
    toVector(): Vector<T> {
        return <any>undefined;
    }
}

interface Seq<T> {
    tail(): Option<Seq<T>>;
}

class Vector<T> implements Seq<T> {

    tail(): Option<Vector<T>> {
        return <any>undefined;
    }

     // the next line breaks the compilation
    partition2<U extends T>(predicate:(v:T)=>v is U): [Vector<U>,Vector<Exclude<T,U>>];
    partition2(predicate:(x:T)=>boolean): [Vector<T>,Vector<T>];
    partition2<U extends T>(predicate:(v:T)=>boolean): [Vector<U>,Vector<any>] {
        return <any>undefined;
    }
}

The new line is the first overload for partition2. If you comment on this, everything builds perfectly.

If you compile this with --strict, it will fail with an error:

t.ts(13,5): error TS2416: Property 'tail' in type 'Vector<T>' is not assignable to the same property in base type 'Seq<T>'.
  Type '() => Option<Vector<T>>' is not assignable to type '() => Option<Seq<T>>'.
    Type 'Option<Vector<T>>' is not assignable to type 'Option<Seq<T>>'.
      Types of property 'toVector' are incompatible.
        Type '() => Vector<Vector<T>>' is not assignable to type '() => Vector<Seq<T>>'.
          Type 'Vector<Vector<T>>' is not assignable to type 'Vector<Seq<T>>'.
            Types of property 'tail' are incompatible.
              Type '() => Option<Vector<Vector<T>>>' is not assignable to type '() => Option<Vector<Seq<T>>>'.
                Type 'Option<Vector<Vector<T>>>' is not assignable to type 'Option<Vector<Seq<T>>>'.
                  Types of property 'toVector' are incompatible.
                    Type '() => Vector<Vector<Vector<T>>>' is not assignable to type '() => Vector<Vector<Seq<T>>>'.
                      Type 'Vector<Vector<Vector<T>>>' is not assignable to type 'Vector<Vector<Seq<T>>>'.
                        Types of property 'tail' are incompatible.
                          Type '() => Option<Vector<Vector<Vector<T>>>>' is not assignable to type '() => Option<Vector<Vector<Seq<T>>>>'.
                            Type 'Option<Vector<Vector<Vector<T>>>>' is not assignable to type 'Option<Vector<Vector<Seq<T>>>>'.
                              Types of property 'toVector' are incompatible.
                                Type '() => Vector<Vector<Vector<Vector<T>>>>' is not assignable to type '() => Vector<Vector<Vector<Seq<T>>>>'.
                                  Type 'Vector<Vector<Vector<Vector<T>>>>' is not assignable to type 'Vector<Vector<Vector<Seq<T>>>>'.
                                    Types of property 'tail' are incompatible.
                                      Type '() => Option<Vector<Vector<Vector<Vector<T>>>>>' is not assignable to type '() => Option<Vector<Vector<Vector<Seq<T>>>>>'.
                                        Type 'Option<Vector<Vector<Vector<Vector<T>>>>>' is not assignable to type 'Option<Vector<Vector<Vector<Seq<T>>>>>'.
                                          Types of property 'toVector' are incompatible.
                                            Type '() => Vector<Vector<Vector<Vector<Vector<T>>>>>' is not assignable to type '() => Vector<Vector<Vector<Vector<Seq<T>>>>>'.
                                              Type 'Vector<Vector<Vector<Vector<Vector<T>>>>>' is not assignable to type 'Vector<Vector<Vector<Vector<Seq<T>>>>>'.
                                                Type 'Vector<Vector<Vector<Seq<T>>>>' is not assignable to type 'Vector<Vector<Vector<Vector<T>>>>'.

I really don't know what to do to make this work: - (

+4
source
2

, (, , ). , , :

interface A<T> {
    bat: B<A<T>>;
}

interface B<T> extends A<T> {
    bat: B<B<T>>;
    boom: true
}

. , , Y X, A<Y> A<X> B<Y> B<X>. B<T> A<T>, , , , B<B<T>> B<A<T>>. , bat B B<A<T>> B<B<T>>.


, , ( ) B:

interface A<T> {
    bat: B<A<T>>;
}
interface B<T> extends A<T> {
//        ^ error
// Interface 'B<T>' incorrectly extends interface 'A<T>'.
    bat: B<B<T>>;

    boom: T extends any ? true : true
}

. boom, , true, - . , , B<T> A<T>, , B<B<T>> B<A<T>>, B<B<B<T>>> B<B<A<T>>> ... , .

, - , ... , . , , B<T> A<T>, ( " ", , ).


, - , , GitHub. , .

, - . , .

!

+4

, Seq<T>.tail Option<Seq<T>>, Vector<T>.tail Option<Vector<T>>. , . - Seq<T>, Option , , , . , tail Vector<T> Option<Vector<T>>, , tail Seq. , this:

export class Option<T> {
    toVector(): Vector<T> {
        return <any>undefined;
    }
}

interface Seq<T> {
    tail(): Option<this>;
}

class Vector<T> implements Seq<T> {

    tail(): Option<this> {
        return <any>undefined;
    }

    // the next line breaks the compilation
    partition2<U extends T>(predicate:(v:T)=>v is U): [Vector<U>,Vector<Exclude<T,U>>];
    partition2(predicate:(x:T)=>boolean): [Vector<T>,Vector<T>];
    partition2<U extends T>(predicate:(v:T)=>boolean): [Vector<U>,Vector<any>] {
        return <any>undefined;
    }
}

declare var v: Vector<number>;
var d = v.tail().toVector() // will be Vector<Vector<number>>
+3

Source: https://habr.com/ru/post/1695285/


All Articles