UNPKG

rivo

Version:

🤖 The ultimate library you need for composable type-level programming in TypeScript, powered by HKT.

218 lines (205 loc) • 5.9 kB
import type ElemFn from "./Elem"; import type IsFixedLengthFn from "./IsFixedLength"; import type IsReadonlyFn from "./IsReadonly"; import type IsTupleFn from "./IsTuple"; import type IsWritableFn from "./IsWritable"; import type MixFn from "./Mix"; import type MutateFn from "./Mutate"; import type OfReadonlyFn from "./OfReadonly"; import type OfWritableFn from "./OfWritable"; import type { PartialApply } from "../HKT"; import type { Lazied, Lazied$Get } from "../helpers"; /** * Alias for `readonly T[]` to represent an `Array` or `ReadonlyArray`. */ export type Ary<T = unknown> = readonly T[]; /** * {@link Lazied} version of {@link Ary}. */ export interface AryL<L extends Lazied> extends Ary<Lazied$Get<L>> {} /** * Alias for `readonly T[]`. */ export type ReadonlyAry<T> = readonly T[]; /** * {@link Lazied} version of {@link ReadonlyAry}. */ export interface ReadonlyAryL<L extends Lazied> extends ReadonlyAry<Lazied$Get<L>> {} /** * Alias for `T[]`. */ export type WritableAry<T> = T[]; /** * {@link Lazied} version of {@link WritableAry}. */ export interface WritableAryL<L extends Lazied> extends WritableAry<Lazied$Get<L>> {} /*********** * Methods * ***********/ /** * Methods for `Array` and `ReadonlyArray`. */ export namespace Ary { /** * [Fn] Get the element type of an {@link Ary} (i.e., `Array` or `ReadonlyArray`). * * Sig: `<T>(a: Ary<T>) => T` * * @example * ```typescript * type R1 = $<Ary.Elem, readonly string[]>; * // ^?: string * type R2 = $<Ary.Elem, (number | boolean)[]>; * // ^?: number | boolean * type R3 = $<Ary.Elem, []>; * // ^?: never * type R4 = $<Ary.Elem, [1, 2, 3]>; * // ^?: 1 | 2 | 3 * ``` */ export type Elem = ElemFn; /** * [Fn] Check if an {@link Ary} (i.e., `Array` or `ReadonlyArray`) is a fixed length * one (i.e., the `length` property is a number literal). * * Sig: `(a: Ary) => boolean` * * @example * ```typescript * type R1 = $<Ary.IsFixedLength, string[]>; * // ^?: false * type R2 = $<Ary.IsFixedLength, readonly number[]>; * // ^?: false * type R3 = $<Ary.IsFixedLength, ["foo", "bar"]>; * // ^?: true * type R4 = $<Ary.IsFixedLength, readonly [42, 1337, ...string[]]>; * // ^?: false * ``` */ export type IsFixedLength = IsFixedLengthFn; /** * [Fn] Check if an {@link Ary} (i.e., `Array` or `ReadonlyArray`) is a tuple. * * Sig: `(a: Ary) => boolean` * * @example * ```typescript * type R1 = $<Ary.IsTuple, string[]>; * // ^?: false * type R2 = $<Ary.IsTuple, readonly number[]>; * // ^?: false * type R3 = $<Ary.IsTuple, ["foo", "bar"]>; * // ^?: true * type R4 = $<Ary.IsTuple, readonly [42, 1337, ...string[]]>; * // ^?: true * type R6 = $<Ary.IsTuple, readonly [...string[]]>; * // ^?: false, because `readonly [...string[]]` is actually equal to `readonly string[]`, and * // the same is true for something like `[...(number | string)[]]`, which is equal * // to `(number | string)[]`, etc. * type R7 = $<Ary.IsTuple, []>; * // ^?: true * ``` */ export type IsTuple = IsTupleFn; /** * [Fn] Check if an {@link Ary} (i.e., `Array` or `ReadonlyArray`) is readonly. * * Sig: `(a: Ary) => boolean` * * @example * ```typescript * type R1 = $<Ary.IsReadonly, string[]>; * // ^?: false * type R2 = $<Ary.IsReadonly, readonly number[]>; * // ^?: true * type R3 = $<Ary.IsReadonly, ["foo", "bar"]>; * // ^?: false * type R4 = $<Ary.IsReadonly, readonly [42, 1337, ...string[]]>; * // ^?: true * ``` */ export type IsReadonly = IsReadonlyFn; /** * [Fn] Check if an {@link Ary} (i.e., `Array` or `ReadonlyArray`) is writable (i.e., * not readonly). * * Sig: `(a: Ary) => boolean` * * @example * ```typescript * type R1 = $<Ary.IsWritable, string[]>; * // ^?: true * type R2 = $<Ary.IsWritable, readonly number[]>; * // ^?: false * type R3 = $<Ary.IsWritable, ["foo", "bar"]>; * // ^?: true * type R4 = $<Ary.IsWritable, readonly [42, 1337, ...string[]]>; * // ^?: false * ``` */ export type IsWritable = IsWritableFn; /** * [Fn] Mix a type with the element type of an {@link Ary} (i.e., `Array` or * `ReadonlyArray`). * * Sig: `<T, U>[y: U](a: Ary<T>) => Ary<T | U>` * * @example * ```typescript * type R1 = $<Ary.Mix<number>, string[]>; * // ^?: (string | number)[] * type R2 = $<Ary.Mix<"foo">, readonly number[]>; * // ^?: readonly (number | "foo")[] * ``` */ export type Mix<U> = PartialApply<MixFn, [U]>; /** * [Fn] Mutate the element type of an {@link Ary} (i.e., `Array` or `ReadonlyArray`). * * Sig: `<T, U>[y: U](a: Ary<T>) => Ary<U>` * * @example * ```typescript * type R1 = $<Ary.Mutate<number>, string[]>; * // ^?: number[] * type R2 = $<Ary.Mutate<"foo">, readonly number[]>; * // ^?: readonly "foo"[] * ``` */ export type Mutate<U> = PartialApply<MutateFn, [U]>; } /****************** * Static members * ******************/ /** * [Fn] Build a readonly array from a type. * * Sig: `<T>(x: T) => ReadonlyArray<T>` * * @example * ```typescript * type R1 = $<Ary$$OfReadonly, number>; * // ^?: readonly number[] * type R2 = $<Ary$$OfReadonly, 42 | string>; * // ^?: readonly (42 | string)[] * ``` */ export type Ary$$OfReadonly = OfReadonlyFn; /** * [Fn] Build a writable array from a type. * * Sig: `<T>(x: T) => Array<T>` * * @example * ```typescript * type R1 = $<Ary$$OfWritable, number>; * // ^?: number[] * type R2 = $<Ary$$OfWritable, 42 | string>; * // ^?: (42 | string)[] * ``` */ export type Ary$$OfWritable = OfWritableFn; /**************** * Type classes * ****************/ export type { Ary$$Show } from "./Show";