Razumijevanje TypeScript predloška doslovnog tipa s '$ {any}$ {any}'
Može li netko objasniti zašto ovo:
type NotEmpty<T extends string> = T extends `${any}${any}` ? T : never;
declare function something<T extends string>(x: NotEmpty<T>): void;
something("hello")
something(""); // Argument of type 'string' is not assignable to parameter of type 'never'.(2345)
postiže očiti cilj takvog tipa, a ipak ovo ne:
type NotEmpty<T extends string> = T extends `${string}${string}` ? T : never;
declare function something<T extends string>(x: NotEmpty<T>): void;
something("hello")
something(""); // okay
i također ovo ne:
type NotEmpty<T extends string> = T extends `${any}` ? T : never;
declare function something<T extends string>(x: NotEmpty<T>): void;
something("hello")
something(""); // okay
Odgovor #1
Iskreno, iznenađen sam da prvi radi: intuitivno biste pomislili da '' proširuje string koji proširuje bilo koji.
¯\(ツ)/¯
Evo radnog tipa koji može koristiti bilo koja buduća osoba koja treba jedan jednostavan.
type NonEmpty<T extends string> = '' extends T ? never : T;
Ali ovo izgleda kao varanje jer eksplicitno koristi prazni niz i ne odgovara na tvoje pitanje.
Međutim, ako proširite bilo $ {any}$ {any} ili $ {string}$ {string} koristeći infer, oba daju očekivani rezultat.
type NonEmpty<T extends string> = T extends `${infer First}${infer Rest}` ?
First extends string ? Rest extends string ? T : never : never : never;
što samo dodatno povećava moju zbunjenost. Znam da postoje neka pojednostavljenja tipova kada su u pitanju predlošci literala. Mislim da bi najbolji put do odgovora bio otvoriti problem na Typescript repozitoriju i nadati se da će Anders (tip za Typescript) ili netko iz tima pojasniti.
