二分搜索
2017-07-23 11:57
246 查看
二分搜索
看到优化O(logn)时间复杂度问题, 一般用二分搜索模板
int start = 0, end = array.size()-1, mid; while (start + 1 < end){ //该结束条件表示:当start与end指针相邻(start + 1 == end),或者相交,或者错开 时终止,**一般是相邻时终止**。 mid = start + (end - start) / 2; 比较 A[mid] 与 target, 并且挪动 start 与 end 指针 } 此时,start与end相邻,分别判断start 与 end 谁是我们需要寻找的节点。
经典难题
寻找两个数组中第k大的元素 (O(log(m+n)))
这个问题最暴力方法是分别将两个数组按照大小合并为一个数组,新数组的第k个就是答案。以下基于此优化看到O(log)级别的时间复杂度首先想到用二分搜索解决,但是难点在于如何每次将问题模型减小一半?
- 二分减小问题规模
问题给定了两个数组,从直观上很容易想到分别将k/2的数据分给A、B两个数组,去比较它们k/2位置元素的大小。但如何通过比较大小的结果来减小问题的规模呢?
第k个元素不可能出现在k/2位置较小的那个数组里,反证法可以证明:
假设B[k/2]
int findkth(vector<int> A, int startA, vector<int> B, int startB, int k) { //考虑存在空数组 //并且startA与startB移动过程也可能移出所有元素,此时相当于A或B为空 if (startA >= A.size()) { return B[startB + k - 1]; } if (startB >= B.size()) { return A[startA + k - 1]; } if (k == 1) { return A[startA] < B[startB] ? A[startA] : B[startB]; } int A_key = startA + k/2 - 1 < A.size() ? A[startA + k/2 - 1] : INT_MAX; int B_key = startB + k/2 - 1 < B.size() ? B[startB + k/2 - 1] : INT_MAX; if (A_key < B_key) { return findkth(A, startA + k/2, B, startB, k - k / 2); } else { return findkth(A, startA, B, startB + k / 2, k - k / 2); } }
相关文章推荐
- codforces Codeforces Round #409 div2 C 二分搜索
- 查找算法——————二分搜索
- POJ 2455 Secret Milking Machine(搜索-二分,网络流-最大流)
- UVALive 6902 Three Squares(二分 + 搜索)
- 搜索—二分三分搜索—1004
- UVALive 6168 Fat Ninjas --二分小数+搜索
- 搜索算法-二分搜索(折半查找)
- POJ 3258 River Hopscotch【二分搜索】
- poj 1330 Nearest Common Ancestors(LCA 基于二分搜索+st&rmq的LCA)
- 《挑战程序设计竞赛》3.1.3 二分搜索-查找第k大的值 POJ3579 3685
- 二分搜索及其变形应用
- NYOJ586. 疯牛(贪心+二分搜索)
- 二分搜索问题(未理解)
- 二分搜索树
- hdu 1075 二分搜索
- 二分搜索
- 超级赛亚ACMer 二分搜索 upper_bound
- 数据结构_ST算法+二分搜索_GCD问题
- HDU 2199 Can you solve this equation?(二分搜索)
- 以 lower_bound 函数入门二分搜索(形成自己的代码风格)