typescript - Nästlad tuplet spridningsdistributivitet


Idag stötte jag på detta:

type Test = [...[1]|[3], 2]
//   ^? type Test = [1, 2] | [3, 2]

Vad är detta? Är det dokumenterat någonstans?

Om jag gör detta istället får jag det förväntade beteendet:

type Test = [...[1|3], 2]
//   ^? type Test = [1 | 3, 2] 

Jag letar inte efter en lösning här utan snarare efter att förstå vad som pågår.

Svar #1

Det är faktiskt dokumenterat. Se PR:et för Variadic-tupletyper:

När typargumentet för T är en unionstyp, sprids unionen över tuplet-typen. Till exempel, [A, ...T, B] instanserad med X | Y | Z som typargument för T ger en union av instanseringar av [A, ...T, B] med X, Y och Z som typargument för T respektive.

Ditt andra exempel distribueras inte eftersom typen av spridningselementet inte är en union, utan snarare en tuppel som innehåller en union som sitt första element.

Svar #2

Tänk på detta:

type Test = [...[]|[1][3,4,5], 2];

// which is equivalent to
type Test = [2] | [1,2] | [3,4,5,2];

Ditt exempel är bara ett specialfall där båda tuplerna du sprider har bara ett enda objekt. Där [1,2]|[3,2] råkar vara ekvivalent med [1|3, 2]. Men även med två tupler av längd 2 kan resultaten vara mycket olika:

type Test = [...[1,2]|[3,4], 5];
// results in 
type Test = [1,2,5] | [3,4,5];

// and is not the same as
type NotTest = [1|3, 2|4, 5];
// because that means:
type NotTest = [1,2,5] | [1,4,5] | [1,3,5] | [1,4,5];