力扣209.長度最小子數(shù)組
https://leetcode.cn/problems/minimum-size-subarray-sum/
在這道題中要注意的不僅僅是滑動窗口的問題,更重要的問題是在循環(huán)控制中,不恰當(dāng)?shù)恼Z法使用會導(dǎo)致這道題出現(xiàn)很嚴(yán)重的問題,這導(dǎo)致我做這道題做了很多天,真的很崩潰。
代碼問題
先來看一下循環(huán)的控制問題,下面是我之前的錯誤代碼實例:
class Solution {
public:
int minSubArrayLen(int target, vector<int>& nums) {
int left = 0, right = 0;
int sum = 0;
int retsize = 0;
while(right < nums.size())
{
if(sum < target)
sum += nums[right++];
else
{
int size = right - left;
if(retsize == 0 || retsize > size)
retsize = size;
if(sum > target)
{
while(sum >= target)
sum -= nums[left++];
int size = right - left + 1;
if(retsize > size)
retsize = size;
}
}
}
if(sum > target)
{
while(sum >= target)
sum -= nums[left++];
int size = right - left + 1;
if(retsize > size)
retsize = size;
}
return retsize;
}
};
emmmm,之前寫的代碼中最主要的問題就在使用while循環(huán)的同時,right的移動是在滿足條件之后才可以移動,這會導(dǎo)致代碼變得非?;靵y。
所以在寫代碼的過程中,最好要保證一個變量是隨著循環(huán)規(guī)律性發(fā)生變換,而出些需要特殊處理的情況的時候,再對其進行特殊處理,盡可能保證代碼不會很亂而造成越界或者邊界的控制問題。
所以修改后的代碼如下:
class Solution {
public:
int minSubArrayLen(int target, vector<int>& nums) {
int left = 0, right = 0;
int sum = 0;
int retsize = 0;
while(right < nums.size())
{
sum += nums[right++];
if (sum >= target)
{
while (sum >= target)
{
int size = right - left;
if (retsize == 0 || retsize > size)
retsize = size;
sum -= nums[left++];
}
}
}
return retsize;
}
};
滑動窗口問題
滑動窗口問題其實很簡單,就上面這道題而言,如果講這道題設(shè)計為暴力枚舉的解法,那么時間復(fù)雜度為O(n^2),但本質(zhì)上我們可以利用單調(diào)性規(guī)避很多沒必要的枚舉行為:
起始位置時,right和left兩個指針指向同一個位置,left為左邊界,right為右邊界,之后移動右邊界并記錄邊界范圍內(nèi)的值的總和。
當(dāng)right移動到這個位置的時候,范圍內(nèi)的數(shù)據(jù)總和已經(jīng)超過target(7),那么right繼續(xù)向后移動,必定會導(dǎo)致在符合大于target值的基礎(chǔ)上而這個范圍在繼續(xù)擴大。那么就可以確定不需要移動right,但是此時總和已經(jīng)大于target了,所以接下來就要移動left,但是每次移動我們并不知道移動之后是否還滿足條件,所以要進行循環(huán)判斷。文章來源:http://www.zghlxwxcb.cn/news/detail-515437.html
代碼就不貼了,上面有可以參考。這道題看起來很簡單,但最主要的是循環(huán)控制問題,切忌在循環(huán)體中使用條件控制循環(huán)變量的增減,否則會導(dǎo)致邊界很難控制。另外就是滑動窗口問題,滑動窗口利用了單調(diào)性,規(guī)避了很多沒必要的枚舉,這是滑動窗口的核心,它決定了哪些題目可以使用滑動窗口,哪些不可以。文章來源地址http://www.zghlxwxcb.cn/news/detail-515437.html
到了這里,關(guān)于算法筆記--滑動窗口的文章就介紹完了。如果您還想了解更多內(nèi)容,請在右上角搜索TOY模板網(wǎng)以前的文章或繼續(xù)瀏覽下面的相關(guān)文章,希望大家以后多多支持TOY模板網(wǎng)!