import { Either, map as eitherMap, isLeft, isRight } from '@typed/either' import { List, map as listMap } from '@typed/list' import { Maybe, isJust, isNothing, map as maybeMap } from '@typed/maybe' import { curry2 } from '@typed/functions' import { isPromiseLike } from '@typed/logic' /** * Map over the value contained in a data structure. * Works for `List`, `Maybe`, `Either`, and `PromiseLike` data strctures. * @name map(f: (value: A, index: number) => B, list: List): Array */ export const map: Map = curry2(function map(f: (value: any) => any, list: any): any { if (isJust(list) || isNothing(list)) return maybeMap(f, list) if (isLeft(list) || isRight(list)) return eitherMap(f, list) if (isPromiseLike(list)) return Promise.resolve(list.then(f)) return listMap(f, list) }) export type Map = { (f: (value: A, index: number) => B, list: List): Array (f: (value: A) => B, maybe: Maybe): Maybe (f: (value: A) => B, promise: PromiseLike): Promise (f: (value: B) => C, either: Either): Either (f: (value: A, index: number) => B): MapArity1 } export type MapArity1 = { (list: List): Array (maybe: Maybe): Maybe (promise: Promise): Promise (either: Either): Either }