CHAPTER 10 · 综合进阶

贪心、堆与设计题

组合多个基础模型,训练局部决策、优先级维护和数据结构设计。

3 个知识小节7 道分层练习7–10 天 建议周期
展开本章目录
  1. 学习之前
  2. 1. 贪心选择与交换论证
  3. 2. 堆、Top K 与流式数据
  4. 3. 按复杂度组合数据结构
  5. 延伸阅读
  6. 分层练习
  7. 我的笔记
00

BEFORE LEARNING

先理解为什么学

进阶题往往不是新语法,而是把排序、哈希、链表和优先队列组合起来满足特定复杂度约束。

开始前应具备

  • 完成前九章核心题
  • 能独立分析复杂度
  • 理解堆与哈希表的基本操作

完成本章后

  • 识别贪心选择性质
  • 熟悉堆的 Top K 模型
  • 能设计满足复杂度约束的数据结构
01

CORE LESSONS

知识讲义

01

LESSON

贪心选择与交换论证

什么时候想到它?

每一步只需做局部选择,且能证明替换成该选择不会让最终答案更差。

贪心不是“选眼前最好”这么简单。排序通常用来建立选择顺序,交换论证则说明任意最优解都能转换成包含当前贪心选择的解。

推导步骤

  1. 提出局部选择规则
  2. 尝试把最优解的第一步替换成该选择
  3. 证明替换后仍可行且不变差
  4. 扫描过程中维护局部最优边界
思维模板 / 伪代码
sort(candidates, by=greedy_key)
state = initial
for candidate in candidates:
  if feasible(candidate, state): take(candidate); update(state)
02

LESSON

堆、Top K 与流式数据

什么时候想到它?

只关心最大/最小的若干元素,或数据持续到来且需要快速取得当前极值。

固定大小的堆只维护与答案相关的 K 个候选,无需完整排序。两个堆还能把数据分成较小的一半和较大的一半,实时维护中位数。

推导步骤

  1. 决定需要小根堆还是大根堆
  2. 固定 K 时让堆顶成为最容易淘汰的元素
  3. 插入后恢复堆大小或两堆平衡
  4. 结合哈希表先统计频率再入堆
思维模板 / 伪代码
heap = []
for item in stream:
  push(heap, item)
  if len(heap) > k: pop_top(heap)
return heap
03

LESSON

按复杂度组合数据结构

什么时候想到它?

题目定义多个 API,并明确 get、put、删除或随机访问的目标复杂度。

单个结构往往不能同时满足所有操作。LRU 用哈希表 O(1) 定位节点,用双向链表 O(1) 调整最近使用顺序;两者通过同一个节点对象保持一致。

推导步骤

  1. 列出每个 API 的目标复杂度
  2. 为查询、顺序和更新分别选择结构
  3. 定义结构之间共享的键或节点
  4. 逐个处理空、满、更新已有键等边界
思维模板 / 伪代码
get(key): locate in map → move node to recent end
put(key, value): update or insert → evict oldest if full
02

READING

延伸阅读

先读完本站讲义并尝试练习;遇到推导不清的地方,再回到原始教程深入阅读。

03

PRACTICE LADDER

按作用分层练习

题量由知识点决定,不再固定为 5 道。先完成“入门”和“模板”,再做变式与综合;挑战题可以留到复习阶段。

入门认识结构模板独立复现变式迁移条件综合组合技巧挑战延后突破
01

贪心选择与交换论证

3 道 · 依次完成

LC 455入门简单

分发饼干

Assign Cookies

为什么选:排序后用最小可满足资源完成局部匹配。

排序 + 贪心建议 20 分钟
打开 LeetCode ↗
LC 55模板中等

跳跃游戏

Jump Game

为什么选:扫描中维护当前能到达的最远边界。

贪心建议 30 分钟
打开 LeetCode ↗
LC 56综合中等

合并区间

Merge Intervals

为什么选:排序后合并与当前区间相交的候选。

排序 + 贪心建议 35 分钟
打开 LeetCode ↗
02

堆、Top K 与流式数据

3 道 · 依次完成

LC 347模板中等

前 K 个高频元素

Top K Frequent Elements

为什么选:哈希统计频率,再用大小为 K 的堆筛选。

哈希 + 堆建议 40 分钟
打开 LeetCode ↗
LC 215变式中等

数组中的第 K 个最大元素

Kth Largest Element

为什么选:比较堆与快速选择的不同复杂度和使用场景。

堆 / 快速选择建议 35 分钟
打开 LeetCode ↗
LC 295挑战困难

数据流的中位数

Find Median from Data Stream

为什么选:用两个堆持续维护有序数据的中间分界。

双堆建议 60 分钟
打开 LeetCode ↗
03

按复杂度组合数据结构

1 道 · 依次完成

LC 146挑战中等

LRU 缓存

LRU Cache

为什么选:组合哈希表和双向链表满足两个 O(1) API。

哈希 + 双向链表建议 60 分钟
打开 LeetCode ↗
04

PERSONAL NOTEBOOK

我的学习笔记

我如何识别这个模式?今天卡在哪里?下次需要先检查什么?

笔记保存在当前浏览器