微信公众号搜"智元新知"关注
微信扫一扫可直接关注哦!

BFS算法不会在Leetcode上的Rotten Oranges问题中标记所有节点

如何解决BFS算法不会在Leetcode上的Rotten Oranges问题中标记所有节点

我正在研究rotten oranges problem

在给定的网格中,每个单元格可以具有以下三个值之一:

  • 值0代表一个空单元格;
  • 值1代表鲜橙色;
  • 值2代表烂橙。

每分钟,任何新鲜的橙子(与4方向相邻) 烂橙变烂了。

返回直到没有单元格之前必须经过的最小分钟数 有一个新鲜的橙子。如果这不可能,请返回-1。

示例1:

  • 输入:[[1,1,1],[1,0],[0,2]]
  • 输出:4

我已经实现了BFS解决方案。然后,在完成BFS之后,我再次进行迭代以确保没有剩余的新鲜橙子,因为如果剩余了新鲜橙子,那么我必须返回-1。

但是,我发现在最后一个循环中,只有一些值更改为2,而其他一些值仍保持为1。我不确定为什么它们也没有更改为2。

class Solution {
    public int orangesRotting(int[][] grid) {
        //need adjacency list/matrix
        Queue<String> q = new LinkedList<>();
        int[] count = new int[1];
        count[0] = 0;
        for(int i = 0; i < grid.length; i++) {
            for(int j = 0; j < grid[i].length; j++) {
                if(grid[i][j] == 2) {
                    q.add("" + i + j);
                    bfs(grid,i,j,count,q);
                }
            }
        }
        
        for(int i = 0; i < grid.length; i++) {
            for(int j = 0; j < grid[i].length; j++) {
                // does NOT always print correct value: 1 is not changed to 2
                System.out.println(grid[i][j]); 
                if(grid[i][j] == 1) {
                    return -1;  // ... and so this -1 is returned when it shouldn't
                }
            }
        }
        
        return count[0];
    }
    
    private static void bfs(int[][] grid,int i,int j,int[] count,Queue<String> q) {
        while(!q.isEmpty()) {
            String s = q.remove();
            //System.out.println(s); //prints correct indices
            i = Integer.parseInt(s.substring(0,1));
            j = Integer.parseInt(s.substring(1));
            
            if(i - 1 > 0 && grid[i - 1][j] == 1) {
                count[0]++;
                i--;
                grid[i][j] = 2;
                q.add("" + i + j);
            }
            if(i + 1 < grid.length && grid[i + 1][j] == 1) {
                count[0]++;
                i++;
                grid[i][j] = 2;
                q.add("" + i + j);
            }
            if(j - 1 > 0 && grid[i][j - 1] == 1) {
                count[0]++;
                j--;
                grid[i][j] = 2;
                q.add("" + i + j);
            }
            if(j + 1 < grid.length && grid[i][j + 1] == 1) {
                count[0]++;
                j++;
                grid[i][j] = 2;
                q.add("" + i + j);
            }
        }
        
    }
    
}

对于上面引用的示例,我的代码输出-1,因为它在最终循环中仍然找到1,而实际上并没有。

您能帮我弄清楚为什么会这样吗?

解决方法

几个问题:

  • 从不检查第0列或第0行中的单元格是否感染了橙色。当i - 1 > 0为1时,比较i是不正确的,但您还应该检查grid[0][j] ... j也会出现相同的问题。

  • 通过用i修改i--,会影响下一个if条件,这些条件旨在查看i的原始值。因此,您不应更改i的值(也不更改j),而应在不修改grid[i-1][j]的情况下将其分配给i

  • bfs中,将j索引与grid.length进行了错误比较。应该将其与grid[i].length进行比较,因为不能保证网格是正方形。

  • 每个变烂的橙色的计数都会增加,但这不是应该计数的数量。许多桔子会在相同分钟内变烂,您应该只数分钟,而不是桔子。要正确计数,您应该进行两项更改:

    • 只有在您收集了队列中所有烂橙后,才对bfs进行初始呼叫,因为它们都属于分钟0。

    • bfs函数本身中,将新的烂橙子添加到单独的队列中,这样您就可以知道在这一特定分钟中添加了哪些橙子。然后,当原始队列变空时,将第二个队列移至第一个队列,等待一分钟,然后重复。

  • 这没问题,但是不需要将ij作为参数传递给bfs,并且让{{ 1}} 返回计数。

为了使它正常工作,我尝试不对代码进行过多更改:

bfs

肯定有一些方法可以使此过程更有效地运行,例如使用数组而不是队列。

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。