algoalgo-world
algoalgo-world/maze/hunt-and-kill
maze/hunt-and-kill

Hunt and Kill

pick a language to open the code

def hunt_and_kill_maze(w, h, rng):
    links = [0] * (w * h)
    seen = [False] * (w * h)
    seen[0] = True
    room = 0
    while room >= 0:
        open_dirs = [d for d in range(4)
                     if neighbor(room, d) >= 0 and not seen[neighbor(room, d)]]
        if open_dirs:
            d = rng.choice(open_dirs)
            other = neighbor(room, d)
            carve(links, room, other, d)
            seen[other] = True
            room = other
            continue
        room = -1
        for scan in range(w * h):
            if seen[scan]:
                continue
            near = [d for d in range(4)
                    if neighbor(scan, d) >= 0 and seen[neighbor(scan, d)]]
            if not near:
                continue
            d = rng.choice(near)
            carve(links, scan, neighbor(scan, d), d)
            seen[scan] = True
            room = scan
            break
    return links
function huntAndKillMaze(w, h, rng) {
  const links = new Array(w * h).fill(0);
  const seen = new Array(w * h).fill(false);
  const pickDir = (from, want) => {
    const dirs = [];
    for (let d = 0; d < 4; d++) {
      const other = neighbor(from, d);
      if (other >= 0 && seen[other] === want) dirs.push(d);
    }
    return dirs.length === 0 ? -1 : dirs[rng.below(dirs.length)];
  };
  let room = 0;
  seen[0] = true;
  while (room >= 0) {
    const d = pickDir(room, false);
    if (d >= 0) {
      const other = neighbor(room, d);
      carve(links, room, other, d);
      seen[other] = true;
      room = other;
      continue;
    }
    room = -1;
    for (let scan = 0; scan < w * h; scan++) {
      if (seen[scan]) continue;
      const back = pickDir(scan, true);
      if (back < 0) continue;
      carve(links, scan, neighbor(scan, back), back);
      seen[scan] = true;
      room = scan;
      break;
    }
  }
  return links;
}
static int pick_dir(char seen[], int room, int want) {
    int dirs[4];
    int count = 0;
    for (int d = 0; d < 4; d++) {
        int other = neighbor(room, d);
        if (other >= 0 && seen[other] == want) dirs[count++] = d;
    }
    return count == 0 ? -1 : dirs[rand() % count];
}

void hunt_and_kill_maze(int links[], int w, int h) {
    int n = w * h;
    char* seen = calloc(n, 1);
    int room = 0;
    seen[0] = 1;
    while (room >= 0) {
        int d = pick_dir(seen, room, 0);
        if (d >= 0) {
            int other = neighbor(room, d);
            carve(links, room, other, d);
            seen[other] = 1;
            room = other;
            continue;
        }
        room = -1;
        for (int scan = 0; scan < n; scan++) {
            if (seen[scan]) continue;
            int back = pick_dir(seen, scan, 1);
            if (back < 0) continue;
            carve(links, scan, neighbor(scan, back), back);
            seen[scan] = 1;
            room = scan;
            break;
        }
    }
    free(seen);
}
static int pick_dir(const std::vector<char>& seen, int room, char want,
                    std::mt19937& rng) {
    std::vector<int> dirs;
    for (int d = 0; d < 4; d++) {
        int other = neighbor(room, d);
        if (other >= 0 && seen[other] == want) dirs.push_back(d);
    }
    if (dirs.empty()) return -1;
    std::uniform_int_distribution<size_t> pick(0, dirs.size() - 1);
    return dirs[pick(rng)];
}

void hunt_and_kill_maze(std::vector<int>& links, int w, int h,
                        std::mt19937& rng) {
    int n = w * h;
    std::vector<char> seen(n, 0);
    int room = 0;
    seen[0] = 1;
    while (room >= 0) {
        int d = pick_dir(seen, room, 0, rng);
        if (d >= 0) {
            int other = neighbor(room, d);
            carve(links, room, other, d);
            seen[other] = 1;
            room = other;
            continue;
        }
        room = -1;
        for (int scan = 0; scan < n; scan++) {
            if (seen[scan]) continue;
            int back = pick_dir(seen, scan, 1, rng);
            if (back < 0) continue;
            carve(links, scan, neighbor(scan, back), back);
            seen[scan] = 1;
            room = scan;
            break;
        }
    }
}
static int PickDir(bool[] seen, int room, bool want, Random rng) {
    var dirs = new List<int>();
    for (int d = 0; d < 4; d++) {
        int other = Neighbor(room, d);
        if (other >= 0 && seen[other] == want) dirs.Add(d);
    }
    return dirs.Count == 0 ? -1 : dirs[rng.Next(dirs.Count)];
}

static int[] HuntAndKillMaze(int w, int h, Random rng) {
    int n = w * h;
    int[] links = new int[n];
    bool[] seen = new bool[n];
    int room = 0;
    seen[0] = true;
    while (room >= 0) {
        int dir = PickDir(seen, room, false, rng);
        if (dir >= 0) {
            int next = Neighbor(room, dir);
            Carve(links, room, next, dir);
            seen[next] = true;
            room = next;
            continue;
        }
        room = -1;
        for (int scan = 0; scan < n; scan++) {
            if (seen[scan]) continue;
            int back = PickDir(seen, scan, true, rng);
            if (back < 0) continue;
            Carve(links, scan, Neighbor(scan, back), back);
            seen[scan] = true;
            room = scan;
            break;
        }
    }
    return links;
}
static int pickDir(boolean[] seen, int room, boolean want, Random rng) {
    List<Integer> dirs = new ArrayList<>();
    for (int d = 0; d < 4; d++) {
        int other = neighbor(room, d);
        if (other >= 0 && seen[other] == want) dirs.add(d);
    }
    return dirs.isEmpty() ? -1 : dirs.get(rng.nextInt(dirs.size()));
}

static int[] huntAndKillMaze(int w, int h, Random rng) {
    int n = w * h;
    int[] links = new int[n];
    boolean[] seen = new boolean[n];
    int room = 0;
    seen[0] = true;
    while (room >= 0) {
        int dir = pickDir(seen, room, false, rng);
        if (dir >= 0) {
            int next = neighbor(room, dir);
            carve(links, room, next, dir);
            seen[next] = true;
            room = next;
            continue;
        }
        room = -1;
        for (int scan = 0; scan < n; scan++) {
            if (seen[scan]) continue;
            int back = pickDir(seen, scan, true, rng);
            if (back < 0) continue;
            carve(links, scan, neighbor(scan, back), back);
            seen[scan] = true;
            room = scan;
            break;
        }
    }
    return links;
}
watch it run, then read it