矩阵连接的单元格:给定矩阵的位置,用数字k替换连接的单元格

时间:2018-08-05 13:39:36

标签: java algorithm depth-first-search

问题陈述: 给定矩阵1和0以及位置(行,列),将所有连接的单元从该位置替换为k

输入:

0 0 0 0
0 0 1 0
0 1 1 0
0 0 0 0

行= 1,col = 2,k = 2 输出:

0 0 0 0
0 0 2 0
0 2 2 0
0 0 0 0

使用的方法: 递归检查左,右,上和下单元格,并将单元格更新为k。 但是对于角落单元,输出不是预期的结果,我不知道它出了什么问题,有人可以帮助我了解错误的出处吗?

行= 0,col = 1,k = 2 错误的输出:

2 2 0 0
2 2 1 0
0 1 1 0
0 0 0 0

预期输出:

2 2 2 2
2 2 1 2
2 1 1 2
2 2 2 2

import java.util.Arrays;

public class MatrixProblem {

    public static int[][] updateColor(int[][] num, int row, int col, int k) {
        int[][] sol = num.clone();
        updateMat(row,col,num[row][col],k,sol);
        return sol;
    }

    private static void updateMat(int row, int col, int o,int k, int[][] sol) { // o stands for old value
        sol[row][col] = k;
        if(row<0 || col<0 || row>= sol.length || col>= sol[row].length) {
            return;
        }
        if (leftPresent(row,col,o,sol)) {
            updateMat(row,--col,o,k,sol);
        }
        if(rightPresent(row,col,o,sol)) {
            updateMat(row,++col,o,k,sol);
        }
        if(topPresent(row,col,o,sol)) {
            updateMat(--row,col,o,k,sol);
        }
        if(bottomPresent(row,col,o,sol)) {
            updateMat(++row,col,o,k,sol);
        }
    }

    private static boolean leftPresent(int row,int col,int old, int[][] sol) {
        int newCol = --col;
        if(newCol >= 0 && sol[row][newCol] == old) {
            return true;
        }
        return false;
    }

    private static boolean rightPresent(int row,int col,int old, int[][] sol) {
        int newCol = ++col;
        if(newCol < sol[row].length && sol[row][newCol] == old) {
            return true;
        }
        return false;
    }
    private static boolean topPresent(int row,int col,int old, int[][] sol) {
        int newRow= --row;      
        if(newRow>=0  && sol[newRow][col] == old) {
            return true;
        }
        return false;
    }
    private static boolean bottomPresent(int row,int col,int old, int[][] sol) {
        int newRow = ++row;
        if(newRow < sol.length && sol[newRow][col] == old) {
            return true;
        }
        return false;
    }
    public static void main (String[] args) {
        int[][] num = new int[][]{{0,0,0,0},
                                   {0,0,1,0},
                                   {0,1,1,0},
                                   {0,0,0,0}};

            System.out.println(Arrays.deepToString(num1));
            System.out.println(Arrays.deepToString(updateColor(num,1,2,2))); //  row = 1, col = 2 , k = 2
            System.out.println(Arrays.deepToString(num2));
            System.out.println(Arrays.deepToString(updateColor(num,0,1,2))); // row =0 , col=1 , k = 2

    }
}

2 个答案:

答案 0 :(得分:0)

问题是因为您使用前缀递增/递减运算符

updateMat(row,--col,o,k,sol);

下次在同一函数中使用col时,它比实际值小1。进行递归调用时,必须增加/减少行/列的值,而不影响updateMat函数中的 curent 局部变量。

示例:以(0,1)开头,并向左调用updateMat之后,col变为0。然后检查右,上,下和因此,您永远不会到达(0,2)。

尝试一下。

if (leftPresent(row,col,o,sol)) {
    updateMat(row, col - 1, o, k, sol);
}
if(rightPresent(row,col,o,sol)) {
     updateMat(row, col + 1, o, k, sol);
}
if(topPresent(row,col,o,sol)) {
    updateMat(row - 1, col, o, k, sol);
}
if(bottomPresent(row,col,o,sol)) {
    updateMat(row + 1, col, o, k, sol);
}

您可以在每个辅助功能leftPresent等中执行相同的操作,但是不会导致错误/问题。但我还是建议您也更改一下以使其更加清晰。

答案 1 :(得分:0)

评论中讨论的我的版本。

package fun;
import static java.lang.System.out;

public class Fun {
    public static void main(String[] args) {
        int[][] matrix = {
                            {0,0,0,0},
                            {0,0,1,0},
                            {0,1,1,0},
                            {0,0,0,0}           
                         };

        out.println("Initial State");

        for(int i=0;i<matrix.length;++i){
            for(int j=0;j<matrix[i].length;++j){
                out.print(matrix[i][j] + " ");
            }
            out.println();
        }

        // apply depth first search(dfs) to modify connected cells
        updateValues(matrix,0,1,5);

        out.println("Modified State");

        for(int i=0;i<matrix.length;++i){
            for(int j=0;j<matrix[i].length;++j){
                out.print(matrix[i][j] + " ");
            }
            out.println();
        }
    }

    private static void updateValues(int[][] matrix,int row,int col,int new_value){
        boolean[][] visited = new boolean[matrix.length][matrix[0].length];// by default every value is false.
        dfs(matrix,row,col,matrix[row][col],new_value,visited);
    }

    private static void dfs(int[][] matrix,int row,int col,int old_value,int new_value,boolean[][] visited){
        if(!isValidLocation(row,col,matrix.length,matrix[0].length)) return;// if index is valid and not going out of bounds
        if(matrix[row][col] != old_value) return;// since this cell isn't connected.
        if(visited[row][col]) return;// not visiting the same index again once it's visited.

        visited[row][col] = true;// mark visited
        matrix[row][col] = new_value;// modify to new value

        dfs(matrix,row-1,col,old_value,new_value,visited);// up
        dfs(matrix,row+1,col,old_value,new_value,visited);// down
        dfs(matrix,row,col-1,old_value,new_value,visited);// left
        dfs(matrix,row,col+1,old_value,new_value,visited);// right
    }   

    private static boolean isValidLocation(int row,int col,int row_size,int col_size){
        return row >= 0 && row < row_size && col >= 0 && col < col_size;
    }    
}

输出

Initial State
0 0 0 0 
0 0 1 0 
0 1 1 0 
0 0 0 0 
Modified State
5 5 5 5 
5 5 1 5 
5 1 1 5 
5 5 5 5