# 14420 - Royal Rumble
## Brief
You are given a grid with cells containing one of the three numbers: 0, 2, and 5 which changes every generation based on their neighbours. You tasked to find the state of the grid after certain generations.
For detailed explanation, visit [this link](https://acm.cs.nthu.edu.tw/problem/14420/).
## Idea
As you have learned in class, there are structures called 2D arrays which stores datas that can be accessed (read or written) by two numbers, in other words, it's basically like a table or an excel spreadsheet. We can use this to create a grid and read the number somewhat like this:
```c=
int grid[256][256];
int H, W;
int main() {
H = 128; // I believe you know how not to hard-code the number 128.
W = 128;
for(int h = 0; h < H; h++) {
for(int w = 0; w < W; w++) {
scanf("%d", &grid[h][w]);
}
}
// [TODO]
// Try printing out the grid here!
}
```
There shouldn't be a problem printing out the grid at this point. What might be troublesome is how we process the grid.
The idea is pretty simple: you can choose the center of a cell and go through all its neighbours to tally the value. Next, based on the value, you can calculate the value in the next generation. Then, you move on to the other cells and repeat. However, if you change the value in the grid directly, you affect the count in the nearby cells. Instead, it's a good idea to store the calculated values in a temporary grid and copy the values back after everything has been said and done. The outline for the code might look like:
```c=
#include <stdio.h>
int grid[256][256];
int tempGrid[256][256];
int H, W;
void ApplyRuleToGrid();
int CalculateSymbolAt_hw(int h, int w);
int main(){
int days;
// [TODO] : Read in the data
for(int day = 0; day < days; day++) {
ApplyRuleToGrid();
}
// [TODO] : Print out the grid
}
void ApplyRuleToGrid() {
for(int h = 0; h < H; h++) {
for(int w = 0; w < W; w++) {
tempGrid[h][w] = CalculateSymbolAt_hw(h, w);
}
}
for(int h = 0; h < H; h++) {
for(int w = 0; w < W; w++) {
grid [h][w] = tempGrid[h][w];
}
}
}
int CalculateSymbolAt_hw(int h, int w) {
int rockCount = 0, scissorsCount = 0, paperCount = 0;
for(int rowNeighbor = h-1; rowNeighbor <= h+1; rowNeighbor++) {
for(int colNeighbor = w-1; colNeighbor <= w+1; colNeighbor++) {
if(???) //[TODO]: which cells not to include as a neighbor?
continue;
if(grid[rowNeighbor][colNeighbor] == 0) {
rockCount++;
} else if (???) {
???++;
} else if (???) {
???++;
} else {
printf("Hey! Don't cheat at rock paper scissors!\n");
}
}
}
if(rockCount > scissorsCount && rockCount > paperCount) {
return 5;
} else if (??? && ???) {
return ???;
} else if (??? && ???) {
return ???;
} else {
return ???;
}
}
```
With this outline, you can start working on your own. Try solving it by yourself before checking my solution!
## Solution
<details>
<summary>My Solution.</summary>
```c=
#include <stdio.h>
int grid[256][256];
int tempGrid[256][256];
int H, W;
void ApplyRuleToGrid();
int CalculateSymbolAt_hw(int h, int w);
int main(){
int days;
scanf("%d%d%d", &H, &W, &days);
for(int h = 0; h < H; h++) {
for(int w = 0; w < W; w++) {
scanf("%d", &grid[h][w]);
}
}
for(int day = 0; day < days; day++) {
ApplyRuleToGrid();
}
for(int h = 0; h < H; h++) {
for(int w = 0; w < W; w++) {
printf("%d ", grid[h][w]);
}
printf("\n");
}
}
void ApplyRuleToGrid() {
for(int h = 0; h < H; h++) {
for(int w = 0; w < W; w++) {
tempGrid[h][w] = CalculateSymbolAt_hw(h, w);
}
}
for(int h = 0; h < H; h++) {
for(int w = 0; w < W; w++) {
grid[h][w] = tempGrid[h][w];
}
}
}
int CalculateSymbolAt_hw(int h, int w) {
int rockCount = 0, scissorsCount = 0, paperCount = 0;
for(int rowNeighbor = h-1; rowNeighbor <= h+1; rowNeighbor++) {
for(int colNeighbor = w-1; colNeighbor <= w+1; colNeighbor++) {
if(rowNeighbor == h && colNeighbor == w)
continue;
if(rowNeighbor < 0 || rowNeighbor >= H || colNeighbor < 0 || colNeighbor >= W)
continue;
if(grid[rowNeighbor][colNeighbor] == 0) {
rockCount++;
} else if (grid[rowNeighbor][colNeighbor] == 2) {
scissorsCount++;
} else if (grid[rowNeighbor][colNeighbor] == 5) {
paperCount++;
} else {
printf("Hey! Don't cheat at rock paper scissors!\n");
}
}
}
if(rockCount > scissorsCount && rockCount > paperCount) {
return 5;
} else if (paperCount > rockCount && paperCount > scissorsCount) {
return 2;
} else if (scissorsCount > rockCount && scissorsCount > paperCount) {
return 0;
} else {
return grid[h][w];
}
}
```
</details>