shared-utils.ts 1.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263
  1. /**
  2. * Predicate with type guard, used to filter out null or undefined values
  3. * in a filter operation.
  4. */
  5. export function notNullOrUndefined<T>(val: T | undefined | null): val is T {
  6. return val !== undefined && val !== null;
  7. }
  8. /**
  9. * Used in exhaustiveness checks to assert a codepath should never be reached.
  10. */
  11. export function assertNever(value: never): never {
  12. throw new Error(`Expected never, got ${typeof value}`);
  13. }
  14. /**
  15. * Simple object check.
  16. * From https://stackoverflow.com/a/34749873/772859
  17. */
  18. export function isObject(item: any): item is object {
  19. return item && typeof item === 'object' && !Array.isArray(item);
  20. }
  21. export function isClassInstance(item: any): boolean {
  22. return isObject(item) && item.constructor.name !== 'Object';
  23. }
  24. /**
  25. * Given an array of option arrays `[['red, 'blue'], ['small', 'large']]`, this method returns a new array
  26. * containing all the combinations of those options:
  27. *
  28. * @example
  29. * ```
  30. * generateAllCombinations([['red, 'blue'], ['small', 'large']]);
  31. * // =>
  32. * // [
  33. * // ['red', 'small'],
  34. * // ['red', 'large'],
  35. * // ['blue', 'small'],
  36. * // ['blue', 'large'],
  37. * // ]
  38. */
  39. export function generateAllCombinations<T>(
  40. optionGroups: T[][],
  41. combination: T[] = [],
  42. k: number = 0,
  43. output: T[][] = [],
  44. ): T[][] {
  45. if (k === 0) {
  46. optionGroups = optionGroups.filter(g => 0 < g.length);
  47. }
  48. if (k === optionGroups.length) {
  49. output.push(combination);
  50. return [];
  51. } else {
  52. // tslint:disable:prefer-for-of
  53. for (let i = 0; i < optionGroups[k].length; i++) {
  54. generateAllCombinations(optionGroups, combination.concat(optionGroups[k][i]), k + 1, output);
  55. }
  56. // tslint:enable:prefer-for-of
  57. return output;
  58. }
  59. }