https://leetcode-cn.com/problems/max-consecutive-ones-iii/
这个题一看就是滑动窗口的题,但是滑动窗口也有不同的优化方法。
class Solution { public int longestOnes(int[] A, int K) { if (A.length == 0) { return 0; } int fast = 0; int slow = 0; int max = 0; int cur = 0; int count = K; while (fast < A.length) { if (A[fast] == 1) { cur++; } else if (A[fast] == 0) { if(count > 0){ cur++; count--; }else { while (slow < fast && count <= 0) { if (A[slow] == 0) { count++; } slow++; cur--; } if(count > 0) { count--; cur++; } } } max = Math.max(max, cur); fast++; } return max; } }
上面就是我第一次提交的答案,可以看到做的还是很乱的,有很多地方可以优化。具体的思路就是快指针去遍历,遇到0的时候就分两种情况,第一种就是目前可以将0替换成1,那我们直接替换,将K的大小减一。如果没有可以替换的情况,我们就移动慢指针到K大于0.
我这种代码写的还是非常混乱的,特别是在移动慢指针的情况下有很多优化的地方。
public int longestOnes(int[] A, int K) { if (A.length == 0) { return 0; } int fast = 0; int slow = 0; int max = 0; while (fast < A.length) { if(A[fast] == 0){ if(K > 0){ K--; }else{ max = Math.max(max,fast - slow); //这个是个巧妙地地方,A[slow++]==1,我们会访问到当前滑动窗口中第二次出现为0的地方,因为我们判断A[slow] == 1之后,仍然会执行一次slow++ while(A[slow++] == 1); } } fast++; } return Math.max(max,fast-slow); }
第二次写的代码,也是参考了评论区的,我们根本没必要去管等于1的情况,直接右移即可。当我们遇到0并且K小于等于0的情况,这个代码就很巧妙的解决了这个问题。直接寻找当前窗口中第二个0的位置。