算法与数据结构 - 滑动窗口
生活随笔
收集整理的這篇文章主要介紹了
算法与数据结构 - 滑动窗口
小編覺得挺不錯的,現在分享給大家,幫大家做個參考.
滑動窗口
滑動窗口的作用是可以將一部分問題中的嵌套循環轉變為一個單循環,因此可以減少時間復雜度。
滑動窗口的基本思想
難點在于判斷窗口的要求。
例題分析
以 leetcode 第2024題為例:一位老師正在出一場由 n 道判斷題構成的考試,每道題的答案為 true (用 ‘T’ 表示)或者 false (用 ‘F’ 表示)。老師想增加學生對自己做出答案的不確定性,方法是 最大化 有 連續相同 結果的題數。(也就是連續出現 true 或者連續出現 false)。
給你一個字符串 answerKey ,其中 answerKey[i] 是第 i 個問題的正確結果。除此以外,還給你一個整數 k ,表示你能進行以下操作的最多次數:
- 每次操作中,將問題的正確答案改為 ‘T’ 或者 ‘F’ (也就是將 answerKey[i] 改為 ‘T’ 或者 ‘F’ )。
請你返回在不超過 k 次操作的情況下,最大 連續 ‘T’ 或者 ‘F’ 的數目。
輸入:answerKey = "TFFT", k = 1 輸出:3 解釋:我們可以將最前面的 'T' 換成 'F' ,得到 answerKey = "FFFT" 。 或者,我們可以將第二個 'T' 換成 'F' ,得到 answerKey = "TFFF" 。 兩種情況下,都有三個連續的 'F' 。問題實際是在問“在可以改變k個字符的情況下,最大的連續‘T’或‘F’數組的長度是多少”。按照上述分析,對于滑動窗口的要求的直接理解應該是窗口內全部的字符經過 k 次轉換都應該是指定字符,翻譯一下就是窗口內非指定字符的個數不能超過 k,但我們又希望窗口盡可能地大,這樣才能使得連續序列最長。因此對于窗口大小的要求就是窗口內的非指定字符數應維持在 k 個。接下來就可以按照步驟實現滑動窗口解法了:
int slidingWindow(string answerKey, int k, char ch) {// 保存最大的窗口長度int ans = 0;// 保存當前窗口內非指定字符的數量int sum = 0; for (int left=0, right=0; right<answerKey.size(); right++) {// 如果是非指定字符,則sum+1if (answerKey[right] != ch) {sum++; }// 如果窗口尺寸過大,則向右移動left收縮窗口while (sum > k) { if (answerKey[left] != ch) {sum--; }left++;}// 每次移動后都需要判斷最大窗口尺寸是否更新 ans = max(ans, right-left+1);}return ans; }然后我們分別判斷哪一種轉換策略可以得到最長連續序列即可:
int maxConsecutiveAnswers(string answerKey, int k) {return max(slidingWindow(answerKey, k, 'T'), slidingWindow(answerKey, k, 'F')); }總結
以上是生活随笔為你收集整理的算法与数据结构 - 滑动窗口的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 九、【栈和队列】栈和递归
- 下一篇: Visual Studio 2013开发