题外话:看完题目,是不是一头雾水。有疑问就对了,不知道出题者的语文老师看了有啥感想。
题目意思其实很简单,就是给你一个初始坐标点(sr,sc),找和该点附近像素值相同的坐标,而这附近的定义就是上下左右,不包括斜对角;然后将这些像素值替换为新的像素值newColor。
虽然题目是easy,但是对我而言不是easy???????(so sad...
话不多说,直接看解题方法吧!
方法1:广度优先搜索BFS(Broad First Search)
我们从给定的起点开始,进行广度优先搜索。每次搜索到一个方格时,如果其与初始位置的方格颜色相同,就将该方格加入队列,并将该方格的颜色更新,以防止重复入队。
注意:因为初始位置的颜色会被修改,所以我们需要保存初始位置的颜色,以便于之后的更新操作。
class Solution {
public int[][] floodFill(int[][] image, int sr, int sc, int newColor) {
// 题意:油漆桶工具
// 1. 广度优先搜索——queue
int[] dx={0,1,0,-1};
int[] dy={1,0,-1,0}; // 两个数组结合起来看就是右,下,左,上
int m=image.length; // row number
int n=image[0].length; // column numer
Queue<int[]> queue=new LinkedList<>();
int oldColor=image[sr][sc];
if(oldColor==newColor) return image; //特殊情况
queue.offer(new int[]{sr, sc});
image[sr][sc]=newColor;
while(!queue.isEmpty()){ // 广度遍历符合条件的像素点坐
int[] xy=queue.poll();
int x=xy[0],y=xy[1];
for(int i=0;i<4;i++){
int mx=x+dx[i],my=y+dy[i];
if(mx>=0 && mx<m && my>=0 && my<n && image[mx][my]==oldColor){
image[mx][my]=newColor;
queue.offer(new int[]{mx,my});
}
}
}
return image;
}
}
?方法2:假 深度优先搜索
为什么是假?因为本质上还是有广度优先搜索的影子,没有按照一个方向走到底,只是将存储搜索过的坐标数据结构从队列queue变成栈stack。其实本质还是跟方法1一样的。
class Solution {
public int[][] floodFill(int[][] image, int sr, int sc, int newColor) {
// 2. 假深度优先搜索——stack
int[] dx={0,1,0,-1};
int[] dy={1,0,-1,0}; // 两个数组结合起来看就是右,下,左,上
int m=image.length; // row number
int n=image[0].length; // column numer
Deque<int[]> stack=new LinkedList<>();
int oldColor=image[sr][sc];
if(oldColor==newColor) return image;
stack.push(new int[]{sr,sc});
image[sr][sc]=newColor;
while(!stack.isEmpty()){ // 广度遍历符合条件的像素点坐
int[] xy=stack.pop();
int x=xy[0],y=xy[1];
for(int i=0;i<4;i++){
int mx=x+dx[i],my=y+dy[i];
if(mx>=0 && mx<m && my>=0 && my<n && image[mx][my]==oldColor){
image[mx][my]=newColor;
stack.push(new int[]{mx,my});
}
}
}
return image;
}
}
方法3:深度优先搜索DFS(Deep First Search)
我们从给定的起点开始,进行深度优先搜索。每次搜索到一个方格时,如果其与初始位置的方格颜色相同,就将该方格的颜色更新,以防止重复搜索;如果不相同,则进行回溯。
注意:因为初始位置的颜色会被修改,所以我们需要保存初始位置的颜色,以便于之后的更新操作。
class Solution {
int[] dx={0,1,0,-1};
int[] dy={1,0,-1,0}; // 两个数组结合起来看就是右,下,左,上
public int[][] floodFill(int[][] image, int sr, int sc, int newColor) {
// 3.深度优先——递归
int oldColor=image[sr][sc];
if(newColor!=oldColor) dfs(image,sr,sc,newColor,oldColor);
return image;
}
public void dfs(int[][] image, int x, int y, int newColor, int oldColor){
int m=image.length; // row number
int n=image[0].length; // column number
if(!(x>=0 && x<m && y>=0 && y<n)) return;
if(image[x][y]!=oldColor) return;
if(image[x][y]==oldColor){
image[x][y]=newColor;
for (int i=0;i<4;i++){
int mx=x+dx[i],my=y+dy[i];
dfs(image,mx,my,newColor,oldColor);
}
}
}
}
参考:
力扣
|