from itertools import product
import copy
# Grid class with basic functionality
class Grid:
def __init__(self, scale_x, scale_y, content):
self.ScaleX = scale_x
self.ScaleY = scale_y
self.Content = copy.deepcopy(content)
def tile_get(self, index_x, index_y):
return self.Content[index_y][index_x]
def tile_set(self, index_x, index_y, value):
self.Content[index_y][index_x] = value
def tile_move(self, index_x, index_y, repetitions):
sample_index_offsets = [
(+0, +0),
(+1, +0),
(-1, +0),
(+0, +1),
(+0, -1),
]
for sample_index_offset in sample_index_offsets:
sample_index_x = index_x + sample_index_offset[0]
sample_index_y = index_y + sample_index_offset[1]
sample_index_invalid = sample_index_x < 0 or sample_index_x >= self.ScaleX or sample_index_y < 0 or sample_index_y >= self.ScaleY
if sample_index_invalid:
continue
sample_value_this = self.tile_get(sample_index_x, sample_index_y)
sample_value_next = (sample_value_this - repetitions + 10) % 10
self.tile_set(sample_index_x, sample_index_y, sample_value_next)
# Grid setup
grid_scale_x = 7
grid_scale_y = 7
grid_content = [
[0, 0, 5, 3, 2, 2, 3],
[3, 6, 6, 7, 5, 9, 7],
[9, 1, 6, 0, 6, 3, 2],
[4, 2, 3, 0, 4, 3, 3],
[1, 6, 8, 7, 3, 1, 7],
[3, 3, 6, 6, 2, 0, 6],
[7, 5, 6, 2, 3, 9, 9],
]
# Iterate through all possible base row moves (cartesian product)
for grid_moves_base in product(range(10), repeat=grid_scale_x):
# Create grid copy
grid = Grid(grid_scale_x, grid_scale_y, grid_content)
# Apply base row moves to grid
for grid_index_x in range(grid_scale_x):
grid.tile_move(grid_index_x, 0, grid_moves_base[grid_index_x])
# Apply cascading moves to all but the last row, such that said rows have only values zero
for grid_index_y in range(1, grid_scale_y):
for grid_index_x in range(grid_scale_x):
grid.tile_move(grid_index_x, grid_index_y, grid.tile_get(grid_index_x, grid_index_y - 1))
# Check whether or not the last row is only zeroes - and thus the base moves were valid - or not
grid_valid = True
for grid_index_x in range(grid_scale_x):
grid_valid = grid.tile_get(grid_index_x, grid_scale_y - 1) == 0
if not grid_valid:
break
if not grid_valid:
continue
# Note that all the moves can be extrapolated from the base moves
print(grid_moves_base)
break