为什么把问题拆开反而更快?分治算法从主定理到LeetCode完整指南
假设要在一百万个有序数字中找到某个特定值,最直接的想法是从头到尾逐个检查——运气好第一个就是,运气不好要找一百万次。但如果每次都将搜索范围缩小一半,最多只需要20次就能确定结果。这种"分而治之"的智慧,不仅让二分查找成为效率典范,更催生了归并排序、快速选择、Strassen矩阵乘法等一系列经典算法。 ...
假设要在一百万个有序数字中找到某个特定值,最直接的想法是从头到尾逐个检查——运气好第一个就是,运气不好要找一百万次。但如果每次都将搜索范围缩小一半,最多只需要20次就能确定结果。这种"分而治之"的智慧,不仅让二分查找成为效率典范,更催生了归并排序、快速选择、Strassen矩阵乘法等一系列经典算法。 ...
假设你在搜索引擎输入框里键入"goog",下拉列表立刻弹出"google"、“google maps”、“google translate"等一系列建议。这些结果是怎么在毫秒级时间内出现的?如果用哈希表存储所有可能的搜索词,每次按键都需要遍历整个哈希表来找出以当前输入为前缀的词——当词库达到百万级别时,这种做法显然不可行。 ...
假设你正在开发一个社交网络应用,需要实时回答"用户A和用户B是否在同一个社交圈内"这类查询——用户之间可以通过好友关系不断形成更大的圈子。每添加一个好友关系,圈子就可能合并;每查询一次,就需要判断两个用户是否已经连通。如果用传统的图遍历方法,每次查询都可能需要遍历整个图,当用户量达到百万级别时,系统会变得极其缓慢。 ...
1964年,J.W.J. Williams在发表堆排序算法时,顺带发明了一种被称为"堆"的数据结构。他可能没想到,这个最初为排序服务的数据结构,会在六十年后成为每一位程序员面试的必考内容。从操作系统进程调度到网络路由的最短路径计算,从数据库查询优化到实时数据流的中位数统计,堆的身影无处不在。 ...
给定一个迷宫,从入口到出口有多条路径。你应该选择哪种策略?一种方式是沿着每条路一直走到底,走不通就返回上一个分叉口换条路——这就是深度优先搜索。另一种方式是先探索所有离入口距离为1的格子,再探索距离为2的格子,层层推进——这就是广度优先搜索。 ...
给定一组活动,每个活动都有开始时间和结束时间,要求选出最多的互不重叠的活动。最直观的思路是尝试所有可能的组合,但这样的时间复杂度是指数级的。如果换一个角度:每次都选择结束时间最早且不与已选活动重叠的活动,只需要一次遍历就能得到最优解。 ...
给定一个长度为100万的数组,要求找出每个元素右侧第一个比它大的元素。最直观的做法是:对每个元素,向右扫描直到找到更大的元素。最坏情况下,每个元素都需要扫描到数组末尾——总的时间复杂度是$O(n^2)$。 ...