All files flattenDeep.ts

100% Statements 20/20
87.5% Branches 7/8
100% Functions 7/7
100% Lines 20/20

Press n or j to go to the next uncovered block, b, p or k for the previous block.

1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 728x 8x                                                     8x 6x       5x       11x 5x   6x 6x 11x 3x   8x     6x     8x 8x 6x 11x 11x 6x             5x                
import { _reduceLazy, LazyResult } from './_reduceLazy';
import { purry } from './purry';
 
type FlattenDeep<T> = T extends ReadonlyArray<infer K> ? FlattenDeep2<K> : T;
type FlattenDeep2<T> = T extends ReadonlyArray<infer K> ? FlattenDeep3<K> : T;
type FlattenDeep3<T> = T extends ReadonlyArray<infer K> ? FlattenDeep4<K> : T;
type FlattenDeep4<T> = T extends ReadonlyArray<infer K> ? K : T;
 
/**
 * Recursively flattens `array`.
 * Note: In `pipe`, use `flattenDeep()` form instead of `flattenDeep`. Otherwise, the inferred type is lost.
 * @param items the target array
 * @signature P.flattenDeep(array)
 * @example
 *    P.flattenDeep([[1, 2], [[3], [4, 5]]]) // => [1, 2, 3, 4, 5]
 *    P.pipe(
 *      [[1, 2], [[3], [4, 5]]],
 *      P.flattenDeep(),
 *    ); // => [1, 2, 3, 4, 5]
 * @category Array
 * @pipeable
 */
export function flattenDeep<T>(items: readonly T[]): Array<FlattenDeep<T>>;
 
export function flattenDeep<T>(): (
  items: readonly T[]
) => Array<FlattenDeep<T>>;
 
export function flattenDeep() {
  return purry(_flattenDeep, arguments, flattenDeep.lazy);
}
 
function _flattenDeep<T>(items: Array<T>): Array<FlattenDeep<T>> {
  return _reduceLazy(items, flattenDeep.lazy());
}
 
function _flattenDeepValue<T>(value: T | Array<T>): T | Array<FlattenDeep<T>> {
  if (!Array.isArray(value)) {
    return value;
  }
  const ret: any[] = [];
  value.forEach(item => {
    if (Array.isArray(item)) {
      ret.push(...flattenDeep(item));
    } else {
      ret.push(item);
    }
  });
  return ret;
}
 
export namespace flattenDeep {
  export function lazy() {
    return (value: any): LazyResult<any> => {
      const next = _flattenDeepValue(value);
      if (Array.isArray(next)) {
        return {
          done: false,
          hasNext: true,
          hasMany: true,
          next: next,
        };
      }
      return {
        done: false,
        hasNext: true,
        next,
      };
    };
  }
}