Jack
Jack

Reputation: 21

I cant figure out the minesweeper recursive algorithm

I cannot figure out the algorithm for revealing empty cells in minesweeper. revealCells is supposed to take a cell, and then check the surrounding cells and reveal them until it finds a mine cell, but for some reason I keep getting an arrayindexoutofbounds exception. Cells is the 2D array of cells in the board. I know I'm not checking for every condition, I just needed to test if it works at all before I added the rest.

public void revealCells(Cell cell){
    row = cell.getRow();
    column = cell.getCol();

    if (row < 0 || row > cells.length - 1|| column < 0 || column > cells.length - 1) return;

    else if(cell instanceof MineCell) return;       

    else if(cell.getMineCount() == 0 && !(cell.isRevealed())){
        cell.reveal();
        revealCells(cells[row+1][column]);
        revealCells(cells[row][column+1]);
        revealCells(cells[row-1][column]);
        revealCells(cells[row][column-1]);
        revealCells(cells[row+1][column+1]);
        revealCells(cells[row-1][column-1]);
    }
    else{
        return;
    }
}

Upvotes: 1

Views: 3591

Answers (1)

willeM_ Van Onsem
willeM_ Van Onsem

Reputation: 476557

That's not surprisingly: you do a recursive call like:

revealCells(cells[row+1][column]);

That means that Java will first fetch cells[row+1][column]. Now you did not do any bounds checks. The bound check in the method is probably rather useless, since you already got the cell by then, so you know that it is a valid coordinate.

In my opinion, you better redesign your system to work with coordinates, instead of cells, and then fetch the cells after the bounds check:

public void revealCells(int row, int column) {
    if (row < 0 || row >= cells.length|| column < 0 || column >= cells[0].length)
        return;

    Cell cell = cells[row][column]; // now we are safe, so fetch the cell
    if(cell instanceof MineCell)
        return;   

    else if(cell.getMineCount() == 0 && !(cell.isRevealed())){
        cell.reveal();
        // call recursive with coordinates, not cells
        revealCells(row-1,column-1);
        revealCells(row-1,column);
        revealCells(row-1,column+1);
        revealCells(row,column-1);
        revealCells(row,column+1);
        revealCells(row+1,column-1);
        revealCells(row+1,column);
        revealCells(row+1,column+1);
    }
}

Upvotes: 3

Related Questions