LeetCode第832题 解题思路
Given a binary matrix A, we want to flip the image horizontally, then invert it, and return the resulting image.
To flip an image horizontally means that each row of the image is reversed. For example, flipping [1, 1, 0] horizontally results in [0, 1, 1].
To invert an image means that each 0 is replaced by 1, and each 1 is replaced by 0. For example, inverting [0, 1, 1] results in [1, 0, 0].
Example 1:
Input: [[1,1,0],[1,0,1],[0,0,0]]
Output: [[1,0,0],[0,1,0],[1,1,1]]
Explanation: First reverse each row: [[0,1,1],[1,0,1],[0,0,0]].
Then, invert the image: [[1,0,0],[0,1,0],[1,1,1]]
Example 2:
Input: [[1,1,0,0],[1,0,0,1],[0,1,1,1],[1,0,1,0]]
Output: [[1,1,0,0],[0,1,1,0],[0,0,0,1],[1,0,1,0]]
Explanation: First reverse each row: [[0,0,1,1],[1,0,0,1],[1,1,1,0],[0,1,0,1]].
Then invert the image: [[1,1,0,0],[0,1,1,0],[0,0,0,1],[1,0,1,0]]
Notes:
1 <= A.length = A[0].length <= 20
0 <= A[i][j] <= 1
对于此题,拿到手后分解成两个步骤,第一步镜像反转,第二步01替换。
镜像反转
涉及到镜像反转时,首先考虑单双问题,通过两重for循环嵌套,实现反转,找到中心轴就要先判断单双问题,然后控制第二层for循环的停止位置。
for(int i=0;i<A.length;i++){
if(A[i].length %2 ==0){
for(int j =0;j<A[i].length/2;j++){
int change = A[i][j];
A[i][j] = A[i][A[i].length-j-1];
A[i][A[i].length-j-1] =change;
}
}
else {
for(int j =0;j<(A[i].length-1)/2;j++){
int change = A[i][j];
A[i][j] = A[i][A[i].length-j-1];
A[i][A[i].length-j-1] =change;
}
}
}
01替换
01替换相比较而言就更加简单,双重for循环+if检查,0换成1,1换成0即可
for(int i=0;i<A.length;i++){
for(int j=0;j<A[i].length;j++){
if(A[i][j] ==0)
A[i][j] =1;
else if(A[i][j] ==1)
A[i][j] =0;
}
}
小结
题目很简单,主要是在思考镜像反转的时候需要多加注意。使用双重for循环是一种和简单但是算法复杂度较高的方法。
Runtime: 1 ms, faster than 89.13% of Java online submissions for Flipping an Image.
Memory Usage: 42.8 MB, less than 10.20% of Java online submissions for Flipping an Image.
算法时间相比较而言不是很快,需观察最优解
分析最优解
class Solution {
public int[][] flipAndInvertImage(int[][] A) {
int C = A[0].length;
for (int[] row: A)
for (int i = 0; i < (C + 1) / 2; ++i) {
int tmp = row[i] ^ 1;
row[i] = row[C - 1 - i] ^ 1;
row[C - 1 - i] = tmp;
}
return A;
}
}
- 镜像反转可以和01置换同时进行,因为两者没有影响。如果先反转再置换和先置换再反转的结果一样,那么可以同时进行。
- 在判断A[i].length时,单双数不需要分开判断,因为单数时对称轴会自己替换自己,也没有任何影响
总结
再进行单双判断时要弄清楚对称轴的影响,尽量少使用for循环嵌套,降低算法复杂度。