Skip to content

Instantly share code, notes, and snippets.

@pesterev
Created December 3, 2020 16:03
Show Gist options
  • Select an option

  • Save pesterev/8eeb4a0aa7a3385fefa056fcef448967 to your computer and use it in GitHub Desktop.

Select an option

Save pesterev/8eeb4a0aa7a3385fefa056fcef448967 to your computer and use it in GitHub Desktop.
Type-level Unique for tuples
type UniqueParser0<T, R extends unknown[], M> = Readonly<T> extends readonly [] ? T : UniqueParser1<T, R, M>
type UniqueParser1<T, R extends unknown[], M> = Readonly<T> extends readonly [infer _] ? T : UniqueParserN<T, R, M>
type UniqueParserN<T, R extends unknown[], M> = Readonly<T> extends readonly [infer A, ...infer B] ? A extends M ? UniqueParserTerm<B, R, M> : UniqueParserTerm<B, [...R, A], M | A> : never
type UniqueParserTerm<T, R extends unknown[], M> = Readonly<T> extends readonly [] ? R : UniqueParserN<T, R, M>
export type UniqueTuple<T> = UniqueParser0<T, [], never>
@pesterev
Copy link
Copy Markdown
Author

pesterev commented Dec 3, 2020

some examples

// test 0

const test0 = [1, 1, 2, 2, 3, 4] as const

type Test0 = UniqueTuple<typeof test0> // Test0 => [1, 2, 3, 4]

// test 1

type Test1 = UniqueTuple<['a', 'a', 'b', 'c']> // Test1 => ['a', 'b', 'c']

// test 2

const test2 = [1, {a: 'hi'}, 'its string', {a: 'hi'}] as const

type Test2 = UniqueTuple<typeof test2> // Test2 => [1, { readonly a: 'hi' }, 'its string']

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment