当前位置: 首页 > news >正文

门户网站制作建设大连百度网站排名优化

门户网站制作建设,大连百度网站排名优化,做昆虫类论文网站,网站备案号信息二分查找 什么是二分查找&#xff1f; 二分查找是一种针对有序集合&#xff0c;每次将要查找的区间缩小一半&#xff0c;直到找到查找元素&#xff0c;或区间被缩小为0。 如何实现二分查找&#xff1f; 实现有3个注意点&#xff1a; 终止条件是 low < high 2.求中点的算…

二分查找

什么是二分查找?

二分查找是一种针对有序集合,每次将要查找的区间缩小一半,直到找到查找元素,或区间被缩小为0。

如何实现二分查找?

实现有3个注意点:

  1. 终止条件是 low <= high
    2.求中点的算法是 low + (high - low)/2
    3.low和high的更新是low=mid+1 即到更大的区间找, high=mid-1  即到更小的区间找。

非递归实现

        // 终止条件low>=high 当low=high时,mid=low+(high-low)/2=low=high,即没有等号将少比较一个点// 中点 mid = low + (high-low)/2 即以low为起点,计算low和high之间的中点// mid<value 找大区间 low=mid+1,mid>value,找小区间,high=mid-1public int binSearch(int[] arr,int n,int value){int low=0;int high=n-1;while(low<=high){int mid=low+((high-low)>>1);//int mid=low+(high-low)/2;if(arr[mid]<value){low=mid+1;} else if(arr[mid]>value){high=mid-1;} else{return mid;}}return -1;}

递归实现

// 二分查找的递归实现
public int bsearch(int[] a, int n, int val) {return bsearchInternally(a, 0, n - 1, val);
}private int bsearchInternally(int[] a, int low, int high, int value) {if (low > high) return -1;int mid =  low + ((high - low) >> 1);if (a[mid] == value) {return mid;} else if (a[mid] < value) {return bsearchInternally(a, mid+1, high, value);} else {return bsearchInternally(a, low, mid-1, value);}
}

二分查找有哪些局限性?

1.  二分查找依赖的是顺序表结构,也就是数组
2.  二分查找要求数据有序
3.  数据量太小不适合二分查找,除非每个数据的操作非常耗时,比如,数组中存储的都是长度超过 300 的字符串,如此长的两个字符串之间比对大小,就会非常耗时。
4.  数据量太大也不适合二分查找,因为数组需要占用大量连续的空间
5.  动态数据不适合二分查找,频繁的插入和删除在数组结构下效率很低

思考题

  1. 如何编程实现“求一个数的平方根”?要求精确到小数点后 6 位。
    可以用牛顿弦切法来求平方跟
    double number = 2; //待求平方根的数
    double xini = 10;//初始点
    while(xinixini - number > 1e-6) {
    xini = (number + xini
    xini)/2/xini;
    }
    // xini为平方根
  2. 我刚才说了,如果数据使用链表存储,二分查找的时间复杂就会变得很高,那查找的时间复杂度究竟是多少呢?
    链表不像数组那样支持随机访问,所以链表主要花的是查找第n个节点的访问的时间。
    第一次需要遍历n/2个节点,
    第二次需要遍历n/4个节点,
    第三次需要遍历n/8个节点,

n/2 + n/4 + n/8 + …
和约等于n,因此算法复杂度为O(n),单考虑到其他二分查找的额外操作,会比直接遍历循环查找慢一些。

二分查找有哪些变体问题?

对于有序数组中有重复元素而言二分查找通常有以下4个变体问题。
查找第一个值等于给定值的元素
查找最后一个值等于给定值的元素
查找第一个大于等于给定值的元素
查找最后一个小于等于给定值的元素

这些都是查找等于给定值的变体问题,想一想,你有什么思路可以实现呢?

如何实现变体的二分查找?

arr[mid]和value的值的比较有三种情况:大于,小于,等于
那对于问题1和2而言我们要特殊处理的等于的情况,
问题3要特殊处理大于等于的情况,
问题4要特殊处理小于等于的情况。
问题1的特殊处理逻辑:
等于的情况下,我们mid的下标有可能是0,即数组的第一个元素,那么我们直接返回mid就好了,
那其余情况就是mid>0,那么我们就看mid的前一个元素是否等于value,如果不等于,说明mid是第一个等于value的元素,也直接返回,
如果等于mid,那么我们就需要在前面的区间去查找了,即 high = mid - 1;

那问题2,3,4和1的处理思路类似,可以试着自己实现。

1

    public int binSearchFirst(int[] arr,int n,int value){int low=0;int high=n-1;while (low<=high) {int mid = low + (high - low) / 2;if(arr[mid]<value){low=mid+1;} else if(arr[mid]>value){high=mid-1;} else{// 需要特殊处理的是等于的情况// 1.看mid是否为第一个元素,是返回mid// 2.看mid的前一个元素是否等于value,不等于返回mid// 3.mid的前一个元素等于value,那么就应该去前面区间找,即 high = mid - 1;if(mid==0||arr[mid-1]!=value) {return mid;}high=mid-1;}}return -1;}

2

    public int binSearchFirst(int[] arr,int n,int value){int low=0;int high=n-1;while (low<=high) {int mid = low + (high - low) / 2;if(arr[mid]<value){low=mid+1;} else if(arr[mid]>value){high=mid-1;} else{// 需要特殊处理的是等于的情况// 1.看是mid否为最后一个元素,是返回mid// 2.看mid的后一个元素是否等于value,不等于返回mid// 3.mid的后一个元素等于value,那么就应该去后面区间找,即 low = mid + 1;if(mid==n-1||arr[mid+1]!=value) {return mid;}low=mid+1;}}return -1;}

3

    public int binSearchFirst(int[] arr,int n,int value) {int low = 0;int high = n - 1;while (low <= high) {int mid = low + (high - low) / 2;if (arr[mid] >= value) {// 主要处理大于等于的情况// 1.看mid是否为第一个元素,是返回mid// 2.看mid的前一个元素是否小于value,是返回mid// 3.前一个元素大于等于value,应该去前面区间找,即high=mid-1if(mid==0||arr[mid-1]<value){return mid;}high = mid - 1;} else {low = mid + 1;}}return -1;}

4

    public int binSearchFirst(int[] arr,int n,int value) {int low = 0;int high = n - 1;while (low <= high) {int mid = low + (high - low) / 2;if (arr[mid] <= value) {// 主要处理大于等于的情况// 1.看mid是否为最后一个元素,是返回mid// 2.看mid的后一个元素是否大于value,是返回mid// 3.后一个元素小于等于value,应该去后面区间找,即low=mid+1if(mid==n-1||arr[mid+1]>value){return mid;}low = mid + 1;} else {high = mid - 1;}}return -1;}

二分查找的实际应用场景?

绝大部分情况能用二分查找解决的问题我们更倾向使用散列表或二叉查找树,
那二分查找其实更适用于近似的查找(范围查找)问题,因为这类问题用上述数据结构都不容易实现。

思考题

我们今天讲的都是非常规的二分查找问题,今天的思考题也是一个非常规的二分查找问题。如果有序数组是一个循环有序数组,比如 4,5,6,1,2,3。针对这种情况,如何实现一个求“值等于给定值”的二分查找算法呢?

我们发现循环数组存在一个性质:以数组中间点为分区,会将数组分成一个有序数组和一个循环有序数组。
 
 如果首元素小于 mid,说明前半部分是有序的,后半部分是循环有序数组;
 如果首元素大于 mid,说明后半部分是有序的,前半部分是循环有序的数组;
 如果目标元素在有序数组范围中,使用二分查找;
 如果目标元素在循环有序数组中,设定数组边界后,使用以上方法继续查找。
 
 时间复杂度为 O(logN)。

http://www.dinnco.com/news/67138.html

相关文章:

  • 网站二级域名品牌网站建设方案
  • 青海网站建设怎么建设有了域名怎么建网站
  • 重庆相册制作长沙seo男团
  • ibm用来做测试的网站上海网站建设优化
  • 临夏网站建设营销软件代理推广
  • devexpress 网站开发网络营销产品的特点
  • 七星彩网站开发公司江东seo做关键词优化
  • 三级网站菜单栏东莞seo外包
  • 孝感市网站建设网站推广哪个好
  • wordpress使用图床长沙网站优化推广
  • 做公司网站详细步骤惠州seo外包平台
  • 豆角网是哪个网站开发的网站推广找
  • 宁波城乡建设局管方网站seo关键词优化公司
  • 嵌入式软件开发面试常见问题长沙seo
  • 地方网站怎么做的福州网站关键词推广
  • 网站制作网站设计自动点击器app
  • 做ppt一般在什么网站软件定制
  • 网站建设专业就业前景搜索网站有哪几个
  • wordpress 添加php长沙seo网站优化公司
  • 西安做网站价格文职培训机构前十名
  • wordpress页脚如何修改seo怎么发外链的
  • 电子产品开发流程seo咨询
  • 免费推广做产品的网站发广告推广平台
  • wordpress服务器加速广东百度seo
  • 网站用户体验诊断竞价托管运营哪家好
  • 国内公司名字可以做国外网站企业官方网站有哪些
  • 做美剧网站侵权网络推广页面
  • 江苏网站备案流程app开发公司有哪些
  • web前端属于什么行业淘宝关键词优化
  • 网站建设关键词布局天津关键词排名推广