function cluster()

in src/cluster.php [20:66]


function cluster<T>(vec<DiffOp<T>> $diff): vec<DiffOp<vec<T>>> {
  $clusters = vec[];
  while (!C\is_empty($diff)) {
    $class = $diff[0]->getDiffOpClass();

    $next = C\find_key($diff, $op ==> $op->getDiffOpClass() !== $class);
    if ($next === null) {
      $clusters[] = $diff;
      break;
    }

    $clusters[] = Vec\take($diff, $next);
    $diff = Vec\drop($diff, $next);
  }

  return Vec\map(
    $clusters,
    $cluster ==> {
      $first = C\firstx($cluster);

      if ($first->isDeleteOp()) {
        return new DiffDeleteOp(
          $first->asDeleteOp()->getOldPos(),
          Vec\map($cluster, $op ==> $op->asDeleteOp()->getContent()),
        );
      }

      if ($first->isInsertOp()) {
        return new DiffInsertOp(
          $first->asInsertOp()->getNewPos(),
          Vec\map($cluster, $op ==> $op->asInsertOp()->getContent()),
        );
      }

      if ($first->isKeepOp()) {
        $first = $first->asKeepOp();
        return new DiffKeepOp(
          $first->getOldPos(),
          $first->getNewPos(),
          Vec\map($cluster, $op ==> $op->asKeepOp()->getContent()),
        );
      }

      invariant_violation('invalid op kind: %s', \get_class($first));
    },
  );
}