滑动窗口最大值(LeetCode 239):从暴力遍历到双端队列的 Go 实现详解
文档教程后端【免费下载链接】interview-gogolang面试题集合https://interview.disign.me/项目地址https://gitcode.com/gh_mirrors/in/interview-go点击查看免费下载本文以 interview-go 仓库中algorithm/docs/sliding-window-maximum.md文档为核心完整解析「滑动窗口最大值」这道经典算法题先给出可直接运行的暴力解法再深入讲解时间复杂度为 O(n) 的双端队列单调队列解法并对照仓库源码 algorithm/sliding-window-maximum.go 验证两种实现的边界处理与测试入口。读完本文你将掌握滑动窗口类问题的通用分析路径以及用 Go 切片模拟双端队列写出线性复杂度的面试满分代码。01、题目描述与示例LeetCode 第 239 题滑动窗口最大值给定一个数组nums有一个大小为k的滑动窗口从数组的最左侧移动到数组的最右侧。你只可以看到在滑动窗口内的k个数字。滑动窗口每次只向右移动一位。请返回滑动窗口中的最大值所构成的数组。示例输入nums [1,3,-1,-3,5,3,6,7]k 3输出[3,3,5,5,6,7]窗口移动过程如下表滑动窗口的位置最大值[1 3 -1] -3 5 3 6 731 [3 -1 -3] 5 3 6 731 3 [-1 -3 5] 3 6 751 3 -1 [-3 5 3] 6 751 3 -1 -3 [5 3 6] 761 3 -1 -3 5 [3 6 7]7窗口每向右移动一位左侧出一个元素、右侧进一个元素因此共有L - k 1个窗口其中L len(nums)。本题对题目本身没有太多需要额外说明的难点在于如何高效地求出每个窗口的最大值。02、思路一暴力遍历求解最容易想到的思路是遍历所有滑动窗口对每个窗口内的k个元素求最大值。假设nums [1,3,-1,-3,5,3,6,7]k 3窗口数为 6外层循环定位每个窗口的起始下标index内层循环扫描窗口内k个元素找出最大值func maxSlidingWindow(nums []int, k int) []int { l1 : len(nums) ret : make([]int, 0) if l1 0 || k 0 { return ret } index : 0 for index l1 { m : nums[index] if index l1-k { break } for j : index 1; j indexk; j { if m nums[j] { m nums[j] } } ret append(ret, m) index } return ret }复杂度分析外层循环执行L - k 1次内层循环每次扫描k个元素总时间复杂度为O((L - k 1) × k) ≈ O(L×k)当k接近L/2时退化为 O(L²) 量级空间复杂度为O(1)不计结果数组仅使用常数个额外变量。暴力解法的优点是实现简单、易于理解适合在面试中先给出作为保底方案缺点是在大规模数据下性能不足无法通过 LeetCode 的大数据量用例。03、思路二双端队列单调队列线性解法暴力解法的主要矛盾在于窗口每滑动一次都需要重新扫描k个元素。如果能复用上一次窗口的最大值信息就能把单次求最大值的时间从 O(k) 降到均摊 O(1)。本题比较经典的解法有队列、DP、堆等多种方式所有思路的主要源头都是在窗口滑动的过程中如何更快地完成查找最大值的过程。而最典型的解法是使用双端队列Deque。3.1 什么是双端队列双端队列是一种同时具有队列和栈性质的数据结构队列中的元素可以从两端弹出或者插入。我们可以利用双端队列来实现一个窗口目的是让该窗口可以做到张弛有度——也就是队列长度动态变化。其实用游标或者其他解法的目的都是一样的就是去维护一个可变长的窗口并在窗口内部动态维护最大值信息。3.2 核心思路队头维护当前窗口最大值算法的核心可以概括为三步维护单调性遍历数组时若当前元素比队尾元素大就将队尾元素祭天出队直到队尾元素不小于当前元素再将当前元素入队。这样队内元素自队头到队尾严格递减队头永远是当前窗口的最大值淘汰过期元素当i k时下标i-k的元素已经滑出窗口若它恰好是队头元素则将其从队头出队收集结果当i k-1时窗口已满队头元素即当前窗口的最大值写入结果数组。整体图解如下假设nums [1,3,-1,-3,5,3,6,7]k 33.3 Go 实现用切片模拟双端队列Go 标准库没有内置双端队列但直接用切片即可模拟队尾操作对应append与queue[:len(queue)-1]队头操作对应queue[1:]。func maxSlidingWindow2(nums []int, k int) []int { ret : make([]int, 0) if len(nums) 0 { return ret } var queue []int for i : range nums { for i 0 (len(queue) 0) nums[i] queue[len(queue)-1] { // 将比当前元素小的元素祭天从队尾出队 queue queue[:len(queue)-1] } // 将当前元素放入 queue 中 queue append(queue, nums[i]) if i k nums[i-k] queue[0] { // 维护队列保证其头元素为当前窗口最大值 queue queue[1:] } if i k-1 { // 放入结果数组 ret append(ret, queue[0]) } } return ret }逐行拆解queue中存放的是元素值且自队头到队尾严格递减因此queue[0]恒为当前窗口的最大值第 6 行的出队循环保证新元素入队后队列仍然单调递减——任何一个比新元素小的旧元素都不可能再成为后续窗口的最大值因为新元素下标更靠后、生命周期更长所以可以安全删除第 10 行nums[i-k] queue[0]当队头元素恰好是滑出窗口的那个值时说明它已经过期需要从队头弹出。这里用值相等判断是安全的因为队内所有值互不重复地保留了单调序列中的关键值第 13 行i k-1时窗口恰好完全进入数组此后每个位置都对应一个完整窗口直接取队头入结果数组。复杂度分析每个元素最多入队一次、出队一次均摊到每次操作是 O(1)整体时间复杂度为O(n)队列最多容纳k个元素空间复杂度为O(k)不计结果数组。04、两种解法对比与源码验证仓库源码 algorithm/sliding-window-maximum.go 同时收录了上述两种实现并通过main函数直接验证func main() { arr : []int{1, 3} fmt.Println(arr[0:1]) nums : []int{1, 3, -1, -3, 5, 3, 6, 7} k : 3 ret : maxSlidingWindow2(nums, k) fmt.Println(ret) }对照源码可以看到两个值得注意的实现细节暴力版补全了边界检查maxSlidingWindow在文档代码基础上增加了if l1 0 || k 0 { return ret }避免空数组或k0时产生越界或死循环这是面试中容易被忽略的健壮性细节单调队列版直接返回空切片maxSlidingWindow2对len(nums) 0提前返回逻辑更简洁。对比维度暴力遍历maxSlidingWindow双端队列maxSlidingWindow2时间复杂度O(n×k)O(n)空间复杂度O(1)O(k)实现难度低易于讲解中需理解单调性维护适用场景小数据量、快速交付大数据量、面试最优解你可以直接在仓库中运行go run algorithm/sliding-window-maximum.go验证输出是否为[3 3 5 5 6 7]。05、延伸思考其他可行解法除了双端队列本题还有两条经典路径理解它们有助于面试时展示知识广度优先队列堆维护一个大顶堆堆顶即窗口最大值窗口滑动时把出窗口的元素标记为惰性删除推迟到它成为堆顶时再弹出。时间复杂度同为 O(n log k)代码相对复杂动态规划 / 分段预处理将数组按k分段分别从左向右、从右向左预处理块内前缀/后缀最大值再按窗口跨越的块组合出每个窗口的最大值时间复杂度 O(n)、空间复杂度 O(n)。06、小结滑动窗口最大值是一道高频面试题核心考点有三窗口数量公式L - k 1所有滑动窗口类问题的公共基础暴力解法兜底O(n×k) 的实现要能快速写出并准确说明复杂度单调队列优化用双端队列在 O(n) 时间内维护窗口内递减序列队头即最大值——这一思想同样适用于滑动窗口最小值滑动窗口中位数等变体题目。对 Go 开发者而言掌握用切片模拟双端队列的技巧还能顺带覆盖 Go 面试中常见的切片截取、扩容、复用等底层细节。建议对照仓库源码 algorithm/sliding-window-maximum.go 亲手运行一遍并尝试把数组元素下标而非元素值存入队列作为进阶练习验证对单调队列原理的理解。赞分享文档教程后端【免费下载链接】interview-gogolang面试题集合https://interview.disign.me/项目地址https://gitcode.com/gh_mirrors/in/interview-go点击查看免费下载相关推荐AlgoNote 算法通关LeetCode 239 滑动窗口最大值——优先队列与单调队列双解法剖析AlgoNote 算法通关LeetCode 239 滑动窗口最大值——优先队列与单调队列双解法剖析 导读 本篇基于「算法通关手册」AlgoNote 仓库的 0教程文档知识库滑动窗口最大值LeetCode 239单调队列题解从裁员比喻到三步套路附 codeforces-go 模板实现滑动窗口最大值LeetCode 239单调队列题解从裁员比喻到三步套路附 codeforces go 模板实现 单调队列Monotone Queue科学计算用 GetQzonehistory 快速完成QQ空间说说备份的完整指南用 GetQzonehistory 快速完成QQ空间说说备份的完整指南 GetQzonehistory 是一个免费的开源 Python 项目专门用来备份自己账网页爬虫数据分析上一篇ReactPy中的SSE客户端实现终极指南教你处理服务器发送事件下一篇tchMaterial-parser智能解析技术如何优化电子课本获取体验创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考

相关新闻

Litmus 混沌工程实战:Azure 实例停止(azure-instance-stop)故障实验完全指南

Litmus 混沌工程实战:Azure 实例停止(azure-instance-stop)故障实验完全指南

云原生运维可观测性 【免费下载链接】litmus Litmus helps SREs and developers practice chaos engineering in a Cloud-native way. Chaos experiments are published at the ChaosHub (https://hub.litmuschaos.io). Community notes is at https://hackmd.io/a4Zu_sH4TZGei…

2026/10/12 3:16:54 阅读更多 →
KurrentDB Webhook Source 连接器完全指南:将外部 Webhook 无缝写入事件流

KurrentDB Webhook Source 连接器完全指南:将外部 Webhook 无缝写入事件流

数据库后端流处理 【免费下载链接】EventStore KurrentDB is a database thats engineered for modern software applications and event-driven architectures. Its event-native design simplifies data modeling and preserves data integrity while the integrated streami…

2026/10/12 3:16:54 阅读更多 →
Kubernetes Python Client 的 V1beta2NodeAllocatableMapping 模型:DRA 节点可分配资源映射机制深入解析

Kubernetes Python Client 的 V1beta2NodeAllocatableMapping 模型:DRA 节点可分配资源映射机制深入解析

后端云原生容器编排 【免费下载链接】python Official Python client library for kubernetes 项目地址: https://gitcode.com/gh_mirrors/python1/python 点击查看 免费下载 本篇技术指南以官方 Python 客户端(kubernetes-python-client)中…

2026/10/12 3:16:54 阅读更多 →

最新新闻

WinForms Chart 时间轴实战:DateTime 转 OADate 与滚动条控制

WinForms Chart 时间轴实战:DateTime 转 OADate 与滚动条控制

简介:这份资源围绕VS自带Chart控件展开,面向需要在WinForms项目中实现时间轴图表的.NET开发者,重点解决x轴按时间刻度显示并配合滚动条浏览长时数据的问题。示例采用从Excel读取数据的方式,x轴时间格式为MM-dd HH:mm:ss:fff&#…

2026/10/12 4:02:25 阅读更多 →
Java微信退款接口实战:从签名、证书到异步回调与对账的完整链路

Java微信退款接口实战:从签名、证书到异步回调与对账的完整链路

简介:这是一份面向Java后端开发者的微信退款接口实现示例资源,聚焦商户在用户发起退款时通过API与微信服务器完成安全交互的完整流程。内容围绕Java网络编程、HTTPS安全通信、PKCS12证书管理、RSA2048数字签名与JSON数据处理展开,适合需要对接…

2026/10/12 4:02:25 阅读更多 →
iOS PDF电子签章实战:PDFKit绘制、坐标系与防篡改校验

iOS PDF电子签章实战:PDFKit绘制、坐标系与防篡改校验

简介:面向iOS开发者的PDF电子签章库,原生渲染与加载,体积控制得较小,适用于合同签署、贷款协议、单据确认等需要电子签章的移动场景,适合有一定Objective-C/iOS原生开发基础的工程师。资源共7个文件,压缩包…

2026/10/12 4:02:25 阅读更多 →
Linux实战100例:故障域分层与高危操作避坑指南

Linux实战100例:故障域分层与高危操作避坑指南

简介:本资源是面向Linux初学者与中级运维人员的实战型学习包,聚焦命令行操作、系统配置与常见故障排查,通过100个经典实例覆盖网络调用、Apache服务配置、错误代码解析等核心场景,帮助读者在真实环境中理解原理、积累排错经验。压…

2026/10/12 4:02:25 阅读更多 →
GLM-4源码包实战:从推理到LoRA微调与部署全流程

GLM-4源码包实战:从推理到LoRA微调与部署全流程

简介:GLM-4代码仓库完整源码包,面向大模型开发者、算法工程师及对本地部署感兴趣的技术爱好者,提供智谱AI第四代GLM系列模型的参考实现与基础使用框架。压缩包内共78个文件,包含Python脚本、YAML部署配置、JSON数据、Markdown说明…

2026/10/12 4:02:25 阅读更多 →
分红时代已死,资本证明时代崛起

分红时代已死,资本证明时代崛起

《分红时代已死,资本证明时代崛起》——下一轮能源周期,市场奖励的不是“投得更多”,而是“证明每一笔钱为何值得花”过去五年,能源公司靠不花钱赢得投资者;未来五年,要靠会花钱。投下去的是资本&#xff0…

2026/10/12 4:01:25 阅读更多 →

日新闻

复古胶片颗粒感噪点合成器:Canvas ImageData 像素高斯杂色注入算法

复古胶片颗粒感噪点合成器:Canvas ImageData 像素高斯杂色注入算法

在数码相机、高清显示屏与现代矢量图形技术高度发达的今天,画面可以做到绝对的锐利、平滑与无瑕。然而,当一张秋日手账插画或拍立得照片过于“平整无瑕”时,往往会散发出一种冰冷生硬的“数码塑料感(Digital Plasticity&#xff0…

2026/10/12 0:00:59 阅读更多 →
活字印刷古籍线装排版:Canvas 竖排文字与栏线自适应算法

活字印刷古籍线装排版:Canvas 竖排文字与栏线自适应算法

在现代网页与移动端设计中,横排(Horizontal Layout)早已经成为了绝对的主流。然而,当我们翻开泛黄的线装古籍、宋版木刻诗集,或是欣赏一张茶道雅集的手写便签时,那种**自上而下纵向书写、自右向左逐列铺展&…

2026/10/12 0:00:59 阅读更多 →
周日晚间的“精神松绑减震器”:无压力情绪倾倒箱与温和轻声陪伴

周日晚间的“精神松绑减震器”:无压力情绪倾倒箱与温和轻声陪伴

每到周日的晚上八点到十点,很多人心里都会悄悄亮起一盏警示灯。 在心理学上,这种现象有一个专门的称谓——“周日夜晚焦虑症(Sunday Scaries)”。明天又是周一,闹钟又要重新在七点响彻卧房;脑海里仿佛有一个…

2026/10/12 0:00:59 阅读更多 →

周新闻

流感时间序列预测实战:ARIMA/LSTM全流程拆解与避坑指南

流感时间序列预测实战:ARIMA/LSTM全流程拆解与避坑指南

简介:基于 ARIMA、LSTM、Transformer 等模型的流感时间序列预测 Python 源码,面向计算机相关专业课程设计与期末大作业学生,以及项目实战学习者。内容覆盖预处理、平稳性检验、定阶、残差分析、多模型对比预测的完整时序建模流程,…

2026/10/12 0:16:30 阅读更多 →
影刀RPA新手教程:键盘模拟输入实战——输入文本与模拟按键的区别

影刀RPA新手教程:键盘模拟输入实战——输入文本与模拟按键的区别

影刀RPA新手教程:键盘模拟输入实战——输入文本与模拟按键的区别 做影刀RPA自动化,十个新手有八个栽在"往输入框里填东西"这件事上:要么填不进去,要么填了一半,要么直接把原来内容追加在后面。这背后的根因&…

2026/10/12 0:16:38 阅读更多 →
影刀RPA新手教程:阅文起点小说数据采集实战——书籍信息与章节内容

影刀RPA新手教程:阅文起点小说数据采集实战——书籍信息与章节内容

影刀RPA新手教程:阅文起点小说数据采集实战——书籍信息与章节内容 1. 认识影刀:什么场景该用RPA采小说数据 起点中文网的页面结构相对稳定——分类榜单、书籍详情、章节内容三块独立页面,跳转链路清晰。这种场景非常适合影刀自动化&#x…

2026/10/12 0:16:43 阅读更多 →

月新闻

我发现了一个新思路:用 Remotion + Claude Code 像写代码一样自动化生成短视频

我发现了一个新思路:用 Remotion + Claude Code 像写代码一样自动化生成短视频

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

2026/10/11 10:45:37 阅读更多 →
Windows下 Codex 中 Chrome 和 Computer Use 插件不可用问题排查及解决参考方式:TaoToken 统一 Key 配置与验证

Windows下 Codex 中 Chrome 和 Computer Use 插件不可用问题排查及解决参考方式:TaoToken 统一 Key 配置与验证

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

2026/10/11 14:36:53 阅读更多 →
黑夜航拍船只数据集训练YOLOV5模型全流程解析

黑夜航拍船只数据集训练YOLOV5模型全流程解析

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

2026/10/11 14:36:54 阅读更多 →