import { CountMap } from "util/count-map";
import { Coll, Collection, CollGen } from "util/collection";

type InputType = { winning: Collection<number>; mine: Collection<number> };

// If blank strings/ints is not enough
export const inputMapper = (inputs: string) => {
  const [_, nums] = inputs.replaceAll("  ", " ").split(": ");
  const [winning, mine] = nums.split(" | ");

  return {
    winning: Coll(...winning.split(" ")).map((n) => parseInt(n, 10)),
    mine: Coll(...mine.split(" ")).map((n) => parseInt(n, 10)),
  };
};

export function solution1(inputs: Collection<InputType>): number {
  return inputs.reduce((prev, curr) => {
    const matching = curr.winning.intersection(curr.mine);

    if (matching.length === 0) {
      return prev;
    }

    const score = 2 ** (matching.length - 1);

    return prev + score;
  }, 0);
}

export function solution2(inputs: Collection<InputType>): number {
  const scores = inputs.map((curr) => {
    const matching = curr.winning.intersection(curr.mine);

    return matching.length;
  });

  const results = CollGen(scores.length, () => 1);

  for (let i = 0; i < scores.length; i++) {
    const multiplier = results[i];
    const followingCards = scores[i];

    if (followingCards === 0) {
      continue;
    }

    for (let j = 1; j <= followingCards; j++) {
      results[i + j] += multiplier;
    }
  }

  return Coll(...results.values()).x.sum();
}
