【Leetcode】33. Search in Rotated Sorted Array

https://leetcode.com/problems/search-in-rotated-sorted-array/description/

一个递增的没有重复元素的数组,做一次移位操作,然后在数组中查找一个元素返回索引,如果没有返回-1。

首先要明白递增数组移位以后的特征,必然是前半段总比后半段大,而且各自内部是有序的。很明显这是一个特殊的二分查找。仍然是取得中间元素a[m],之后的比较过程和常规的二分不同。

以下特征是关键点:一个移位数组被a[m]切为两段,那么必然有一段是有序的,另一段是跳跃的。

我们只需要判断a[m]两侧是有序的还是跳跃的,可以判断左边,即a[low]如果小于等于a[m],说明[low,m]这段闭区间是有序的,那么[m+1, high]就是跳跃的。这里需要注意必须是有等于才行,否则如果只有两个元素,那么a[m]等于a[low],此时[low,m]这段闭区间原则上是有序的,如果不加等号,那么就会判定[m, high]是有序的,这是错误的。举个例子array = {2,1},low = 0, high = 1, m = 0。此时array[low] == array[m],那么如果不加等号判断,就会认为[low, m]是无序的,那么[m, high]是有序的,即{2,1}有序,显然错误。

接下来,是看target的值,只看左侧有序的情况,如果a[low]<=target<=a[m],那么就需要在左半边查找,否则就在右半边。我们只需要找有序的那边,只要不在有序的那段,就在跳跃段查找。如果从跳跃段下手,仍然无法确定是在左侧还是右侧。这里也需要注意必须加上等于的情况,因为我们是在一段有序闭区间里面查找。

代码:

 public int search(int[] nums, int target) {
        if(nums == null)
        	return -1;
        int low = 0, high = nums.length - 1;
        while(low <= high){
        	int m = (low + high) / 2;
        	if(nums[m] == target)
        		return m;
        	if(nums[low] <= nums[m]){
        		if(nums[low] <= target && target <= nums[m])
        			high = m - 1;
        		else 
        			low = m + 1; 
        	}else{
        		if(nums[m] <= target && target <= nums[high])
        			low = m + 1;
        		else
        			high = m - 1;
        	}
        }
        return -1;
    }


  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值