Refactor Diagram structure to use mdspan for grid representation and update related functions

This commit is contained in:
Feiko Wielsma 2025-12-04 15:47:55 +00:00
parent 0b2afd5993
commit c3a8206e55

View file

@ -20,14 +20,16 @@ struct Diagram {
size_t width;
size_t height;
auto mdspan() { return std::mdspan(data.data(), height, width); }
using GridView = std::mdspan<int, std::dextents<size_t, 2>>;
auto grid() { return GridView(data.data(), height, width); }
};
auto printMap(Diagram &diagram) {
auto mdspan = diagram.mdspan();
for (auto row = 0UZ; row != mdspan.extent(0); row++) {
for (auto col = 0UZ; col != mdspan.extent(1); col++) {
std::print("{}", mdspan[row, col]);
auto grid = diagram.grid();
for (auto row = 0UZ; row != grid.extent(0); row++) {
for (auto col = 0UZ; col != grid.extent(1); col++) {
std::print("{}", grid[row, col]);
}
std::println();
}
@ -68,23 +70,23 @@ auto parseMap(const std::string &filename) -> std::expected<Diagram, std::string
auto countMovablePaper(Diagram &diagram) -> long {
long nMovablePaper{};
auto mdspan = diagram.mdspan();
for (auto row = 1UZ; row != mdspan.extent(0) - 1; row++) {
for (auto col = 1UZ; col != mdspan.extent(1) - 1; col++) {
auto grid = diagram.grid();
for (auto row = 1UZ; row != grid.extent(0) - 1; row++) {
for (auto col = 1UZ; col != grid.extent(1) - 1; col++) {
if (mdspan[row, col] == 1) {
if (grid[row, col] == 1) {
// std::print("checking [{},{}]:", row, col);
// shitty kernel
int upLeft = mdspan[row - 1, col - 1];
int up = mdspan[row - 1, col];
int upRight = mdspan[row - 1, col + 1];
int upLeft = grid[row - 1, col - 1];
int up = grid[row - 1, col];
int upRight = grid[row - 1, col + 1];
int left = mdspan[row, col - 1];
int right = mdspan[row, col + 1];
int left = grid[row, col - 1];
int right = grid[row, col + 1];
int downLeft = mdspan[row + 1, col - 1];
int down = mdspan[row + 1, col];
int downRight = mdspan[row + 1, col + 1];
int downLeft = grid[row + 1, col - 1];
int down = grid[row + 1, col];
int downRight = grid[row + 1, col + 1];
// caveman shit
if ((upLeft + up + upRight + left + right + downLeft + down + downRight) < 4) {
@ -102,40 +104,35 @@ auto countMovablePaper(Diagram &diagram) -> long {
auto moveMoveablePaper(Diagram &diagram) -> long {
long totalPaperRemoved{};
auto mdspan = diagram.mdspan();
auto grid = diagram.grid();
constexpr std::array<std::pair<int, int>, 8> offsets = {
{{-1, -1}, {-1, 0}, {-1, 1}, {0, -1}, {0, 1}, {1, -1}, {1, 0}, {1, 1}}};
while (true) {
long currentPaperRemoved = 0;
for (auto row = 1UZ; row != mdspan.extent(0) - 1; row++) {
for (auto col = 1UZ; col != mdspan.extent(1) - 1; col++) {
if (mdspan[row, col] == 1) {
// std::print("checking [{},{}]:", row, col);
// shitty kernal
int neighbors{};
neighbors += mdspan[row - 1, col - 1];
neighbors += mdspan[row - 1, col];
neighbors += mdspan[row - 1, col + 1];
neighbors += mdspan[row, col - 1];
neighbors += mdspan[row, col + 1];
neighbors += mdspan[row + 1, col - 1];
neighbors += mdspan[row + 1, col];
neighbors += mdspan[row + 1, col + 1];
// caveman shit
if (neighbors < 4) {
mdspan[row, col] = 0;
// std::println("Found");
currentPaperRemoved++;
}
for (auto row = 1UZ; row != grid.extent(0) - 1; row++) {
for (auto col = 1UZ; col != grid.extent(1) - 1; col++) {
if (grid[row, col] != 1) {
continue;
}
// std::print("checking [{},{}]:", row, col);
// shitty kernal
int neighbors{0};
for (auto [dr, dc] : offsets) {
// mdspan allows [x, y] indexing natively
neighbors += grid[row + dr, col + dc];
}
if (neighbors < 4) {
grid[row, col] = 0;
// std::println("Found");
currentPaperRemoved++;
}
// std::println();
}
// std::println();
}
if (currentPaperRemoved == 0) {
std::println("Didn't remove any more paper this iteration! Stopping.");
break;