I have an n x m
matrix consisting of non-negative integers. For example:
2 3 4 7 1
1 5 2 6 2
4 3 4 2 1
2 1 2 4 1
3 1 3 4 1
2 1 4 3 2
6 9 1 6 4
Here is a solution that generalizes the good properties of the corners.
Let's assume that we could find a perfect drop point for a given field, that is, a best way to decrease the value in it. Then to find the minimum number of bombs to be dropped, a first draft of an algorithm could be (the code is copy-pasted from a ruby implementation):
dropped_bomb_count = 0
while there_are_cells_with_non_zero_count_left
coordinates = choose_a_perfect_drop_point
drop_bomb(coordinates)
dropped_bomb_count += 1
end
return dropped_bomb_count
The challenge is choose_a_perfect_drop_point
. First, let's define what a perfect drop point is.
(x, y)
decreases the value in (x, y)
. It may also decrease values in other cells.(x, y)
is better than a drop point b for (x, y)
if it decreases the values in a proper superset of the cells that b decreases.(x, y)
are equivalent if they decrease the same set of cells.(x, y)
is perfect if it is equivalent to all maximal drop points for (x, y)
. If there is a perfect drop point for (x, y)
, you cannot decrease the value at (x, y)
more effectively than to drop a bomb on one of the perfect drop points for (x, y)
.
A perfect drop point for a given field is a perfect drop point for any of its cells.
Here are few examples:
1 0 1 0 0
0 0 0 0 0
1 0 0 0 0
0 0 0 0 0
0 0 0 0 0
The perfect drop point for the cell (0, 0)
(zero-based index) is (1, 1)
. All other drop points for (1, 1)
, that is (0, 0)
, (0, 1)
, and (1, 0)
, decrease less cells.
0 0 0 0 0
0 0 0 0 0
0 0 1 0 0
0 0 0 0 0
0 0 0 0 0
A perfect drop point for the cell (2, 2)
(zero-based index) is (2, 2)
, and also all the surrounding cells (1, 1)
, (1, 2)
, (1, 3)
, (2, 1)
, (2, 3)
, (3, 1)
, (3, 2)
, and (3, 3)
.
0 0 0 0 1
0 0 0 0 0
0 0 1 0 0
0 0 0 0 0
0 0 0 0 0
a perfect drop points for the cell (2, 2)
is (3, 1)
: It decreases the value in (2, 2)
, and the value in (4, 0)
. All other drop points for (2, 2)
are not maximal, as they decrease one cell less. The perfect drop point for (2, 2)
is also the perfect drop point for (4, 0)
, and it is the only perfect drop point for the field. It leads to the perfect solution for this field (one bomb drop).
1 0 0 0 0
0 0 0 0 0
0 0 1 0 0
0 0 0 0 0
1 0 0 0 0
There is no perfect drop point for (2, 2)
: Both (1, 1)
and (1, 3)
decrease (2, 2)
and another cell (they are maximal drop points for (2, 2)
), but they are not equivalent. However, (1, 1)
is a perfect drop point for (0, 0)
, and (1, 3)
is a perfect drop point for (0, 4)
.
With that definition of perfect drop points and a certain order of checks, I get the following result for the example in the question:
Drop bomb on 1, 1
Drop bomb on 1, 1
Drop bomb on 1, 5
Drop bomb on 1, 5
Drop bomb on 1, 5
Drop bomb on 1, 6
Drop bomb on 1, 2
Drop bomb on 1, 2
Drop bomb on 0, 6
Drop bomb on 0, 6
Drop bomb on 2, 1
Drop bomb on 2, 5
Drop bomb on 2, 5
Drop bomb on 2, 5
Drop bomb on 3, 1
Drop bomb on 3, 0
Drop bomb on 3, 0
Drop bomb on 3, 0
Drop bomb on 3, 0
Drop bomb on 3, 0
Drop bomb on 3, 4
Drop bomb on 3, 4
Drop bomb on 3, 3
Drop bomb on 3, 3
Drop bomb on 3, 6
Drop bomb on 3, 6
Drop bomb on 3, 6
Drop bomb on 4, 6
28
However, the algorithm only works if there is at least one perfect drop point after each step. It is possible to construct examples where there are no perfect drop points:
0 1 1 0
1 0 0 1
1 0 0 1
0 1 1 0
For these cases, we can modify the algorithm so that instead of a perfect drop point, we choose a coordinate with a minimal choice of maximal drop points, then calculate the minimum for each choice. In the case above, all cells with values have two maximal drop points. For example, (0, 1)
has the maximal drop points (1, 1)
and (1, 2)
. Choosing either one and then calcualting the minimum leads to this result:
Drop bomb on 1, 1
Drop bomb on 2, 2
Drop bomb on 1, 2
Drop bomb on 2, 1
2