TypeScrip: Oh, ce drôle de système de caractères

Bonjour, je m'appelle Dmitry Karlovsky et récemment, avec Artur Mukminov , j'ai organisé un atelier où j'ai montré comment développer des fonctions de type complexes grâce à des tests . C'est 2 heures de programmation de type dur. Alors comme teaser, attrapez une analyse des curiosités du système de type dactylographié.













Les relations sont difficiles



Il est très facile de vérifier si un type est un sous-type d'un autre en utilisant le typoternaire:







type IsAExtendsB = A extends B ? true : false
      
      





Classify, 2 4 :







  • [ A, '<:', B ]



    — A B.
  • [ A, ':>', B ]



    — B A.
  • [ A, '==', B ]



    — ( ).
  • [ A, '!=', B ]



    — .


, Equal Assert, , , . Assert , .







! ..



Object



object



— , , :







type boolean_is_Object = Assert<
    boolean extends Object ? true : false,
    true
>

type boolean_is_not_object = Assert<
    boolean extends object ? true : false,
    false
>
      
      





, , , :







type Object_vs_object = Assert<
    Classify< Object, object >,
    [ Object, '==', object ]
>
      
      





: (, boolean



) (, Object



), — (, object



), — .







, . Object



, object



.









, , — , :







type boolean_is_true_or_false = Assert<
    boolean,
    true | false
>
      
      





:







enum FL4 { Absurd, False, True, Unknown }

type FL4_is_union = Assert<
    FL4,
    | FL4.Absurd | FL4.False | FL4.True | FL4.Unknown
>
      
      





( ):







type Absurd_is_number = Assert<
    Classify< FL4.Absurd, number >,
    [ FL4.Absurd, '==', number ]
>
      
      





:







type Absurd_is_never_wtf = Assert<
    Classify< FL4.Absurd, 0 >,
    [ never, '<:', 0 ]
>
      
      





, , ? , !







type One_is_never_wtf = Assert<
    Classify< FL4.Absurd, 1 >,
    [ FL4.Absurd, ':>', never ]
>
      
      





, , !







, — , :







enum FL3 { Absurd, False, True }

type Absurd_is_not_Absurd = Assert<
    Equal< FL3.Absurd, FL4.Absurd > | false,
    false
>
      
      





, . , , , :







enum HappyDebugging {
    False = "True", 
    True = "False",
}

type True_extends_string = Assert<
    Classify< HappyDebugging.True, string >,
    [ HappyDebugging.True, '<:', string ]
>
      
      





, number



, string



.









, :







  • never



    . , .
  • unknown



    — . . unknown



    .


Mais qu'est-ce qui se profile à côté d'eux? Oui ça l'est any



!
D'une part, il est totalement interchangeable avec unknown



:







type unknown_is_any = Assert<
    unknown,
    any
>
      
      





Mais d'un autre côté, comme le chat de Schrödinger, c'est un sous-type never



(et, par conséquent, de tout autre type de do unknown



) et ne l'est pas en même temps:







type any_maybe_extends_never = Assert<
    any extends never ? true : false,
    true | false
>
      
      





Bref, ça any



casse le fond dans tous les sens possibles. Le sort de ceux qui se retrouvent face à lui est difficile ...













Tout le code de l'article.







Heureux les gars de débogage!














All Articles