At the request of @KyleMit, I have compiled my comments into a single formal block.
If you are dealing with a "dynamic tuple," I recommend referring to the original answer provided on the linked question. This approach tackles the problem from a different angle, which is essential for achieving what the original poster explicitly requests. Instead of creating alternating pairs, it focuses on validating whether something fits within the criteria of alternating pairs.
In this discussion, I will address the challenges associated with creating such a type and propose an alternative representation for the concept of "alternating pairs."
Why is it problematic?
The main obstacle in defining an "alternating pairs" type (or any dynamic "pair" type) lies in the nature of a pair being a tuple. In type theory, a tuple is a product type that stores distinct resident types along with their respective positions.
A type like [T, U]
specifies "A pair where T
represents the first value's type, and U
represents the second value's type." The distinction between [T, U]
and
[T, U, T]</code is significant. While TypeScript tuples resemble JavaScript arrays, the difference holds weight in the type system. A dynamic tuple type is unattainable because a product type is precise and static.</p>
<h3>What about arrays?</h3>
<p>An array is a collection of homogeneous elements. In type theory, an "array" (akin to a cons list) simply needs to encompass the types of its constituents as a whole without considerations for their specific positions or length. For instance, <code>[1, "foo", True]
categorized as an array would carry the type
Array<number | string | boolean>
, reflecting the overall type of its contents without retaining positional information. Any type assignable to
number | string | boolean
may be added to this array.
An alternate perspective
Lets rethink. The objective set by the OP involves a "dynamic, sequential collection of pairs." Such a collection is better represented as an array than a static tuple. Pairing up pairs results in:
[(T, U)]
or [(T, U), (T, U)]
or [(T, U), (T, U), (T, U)]
and so forth
NOTE: The usage of parentheses instead of angle brackets ([[T, U], [T, U]...]
)is merely for clarity.
Homogeneity - the key characteristic required for a dynamic sequential collection. The final type suggested is just Array<[T, U]>
or [T, U][]
- an array of tuples representing pairs, fostering a dynamic sequential collection of pairs.
This approach is recommended for its simplicity and ease of comprehension and maintenance.
Irrelevant details
The assertion that "arrays are homogenous collections in type theory" may not hold true in every scenario. Heterogeneous well-typed arrays do exist in complex type systems but pose challenges in management and are generally irrelevant in a TypeScript context. However, those intrigued by these concepts can explore advanced topics like Haskell with generalized algebraic data types and type families.
It's understandable if those names seem intimidating.
I must confess that my knowledge on this subject has evolved since my earlier comments here, thanks to my exploration of Haskell in recent months :)