二分(折半)查找
2013-11-18 21:22
288 查看
折半查找:又叫二分查找,采用分治思想,适用于不经常变动且查找频繁的表;
算法思想:
将n个元素(假设n个元素升序)分为大致相同的两部分,取data[n / 2] 与目标元素m比较:
若data[n/2] == m:return (n / 2);
若data[n/2] > m:则我们只要在data[]的左半部分继续查找;
若data[n/2] < m:则我们只要在data[]的有半部分继续查找;
时间复杂度:O(logn);
优点:比较次数少,查找速度快,平均性能好;
缺点:要求待查表为"有序表",且插入删除困难;
边界错误问题:
(1)左闭右开区间([left , right))。
left = 0 , right = length;
循环条件while(left < right):
data[middle] > m:right = middle;
data[middle] < m: left = middle + 1;
(2)左右皆闭区间([left , right])。
left = 0 , right = length - 1;
循环条件while(left <= right):
data[middle] > m:right = middle - 1;
data[middle] < m:left = middle + 1;
循环体外的初始化条件与循环体内的初始化条件,在迭代时必须一致的区间规则;
代码实现:
算法思想:
将n个元素(假设n个元素升序)分为大致相同的两部分,取data[n / 2] 与目标元素m比较:
若data[n/2] == m:return (n / 2);
若data[n/2] > m:则我们只要在data[]的左半部分继续查找;
若data[n/2] < m:则我们只要在data[]的有半部分继续查找;
时间复杂度:O(logn);
优点:比较次数少,查找速度快,平均性能好;
缺点:要求待查表为"有序表",且插入删除困难;
边界错误问题:
(1)左闭右开区间([left , right))。
left = 0 , right = length;
循环条件while(left < right):
data[middle] > m:right = middle;
data[middle] < m: left = middle + 1;
(2)左右皆闭区间([left , right])。
left = 0 , right = length - 1;
循环条件while(left <= right):
data[middle] > m:right = middle - 1;
data[middle] < m:left = middle + 1;
循环体外的初始化条件与循环体内的初始化条件,在迭代时必须一致的区间规则;
代码实现:
#include<iostream> #include<exception> using namespace std; //---------------------------------------------二分查找(顺序查找)--------------------------------------- int BinSearch_Soulation1(const int* data , int length , int m) { //左闭右闭区间 int left = 0; int right = length - 1 ; while(left <= right) { //middle = (right + left) / 2 不可取; //若(right + left) 溢出时,出现错误; int middle = left + (right - left) / 2; if(data[middle] > m) { right = middle - 1; } else if(data[middle] < m) { left = middle + 1; } else { return middle; } } return -1; } int BinSearch_Soulation2(const int* data , int length , int m) { //左闭右开区间 int left = 0; int right = length; int middle; while(left < right) { middle = left + ((right - left) / 2); if(data[middle] > m) { right = middle; } else if(data[middle] < m) { left = middle + 1; } else { return middle; } } return -1; } int BinSearch_Soulation3(const int* data, int length, int m) { int left, right, middle; left = -1, right = length; while (left + 1 != right)//这个循环维持的条件是left<right && array[left]<v<=array[right],所以到最后的时候, {//如果可以找到目标,则只剩下两个数,并且满足 array[left]<v<=array[right],是要查找的数是right middle = left + (right - left) / 2; if (data[middle] < m)//必须保证array[left]<v<=array[right],所以left = middle; {//如果left =middle+1,则有可能出现 array[left]<=v的情况 left = middle; } else { right = middle; } } if (right >= length || data[right] != m) { right = -1; } return right; }
相关文章推荐
- 0基础学编程之猜数字游戏,折半二分查找,模拟输入密码及大小写互换
- 二分查找算法、折半搜索、二分搜索
- c语言:代码实现折半(二分)查找
- 三种静态查找算法:顺序、二分/折半、索引/分块查找
- 折半,二分查找问题
- PHP有序表查找----二分查找(折半)
- java冒泡,选择排序及折半(二分)查找
- 用PHP实现折半(二分)查找
- 算法 -- Java实现二分(折半)查找(图解 + 代码实现)
- 折半(二分)查找
- 【FZUOJ 2178】礼物分配 (折半查找+二分)
- 算法:折半查找或二分查找
- 折半(二分)查找
- 有序的静态查找表的折半(二分)查找算法
- 二分(折半)法查找--Java
- 折半,二分查找问题
- JAVA数组排序——二分(折半)查找
- POJ 3977 Subset(折半枚举 + 二分查找)
- java 实现折半(二分)查找
- 二分(折半)查找的详细解说