LeetCode 笔记系列九 Search in Rotated Sorted Array

题目: Suppose a sorted array is rotated at some pivot unknown to you beforehand.

  (i.e., 0 1 2 4 5 6 7 might become 4 5 6 7 0 1 2).

  You are given a target value to search. If found in the array return its index, otherwise return -1.

  You may assume no duplicate exists in the array.

就是说,排序数组可能是右移了一定位数。让你在这个数组中找一个target值。当然用线性查找就没意义了。

想这个解法需要头脑比较清晰。记得原来高中做题,老师最常说的一句话是啥?”要揣摩出题人意图啊“。。。这道题也是这样的。如果是在一个有序数组里面找一个值,那么一般都是用binarySearch。现在数组变了,(当然,还保持一些其他特点,我们下面说),能不能用binarySearch呢,或者我们改一下binarySearch呢?

如果用binarySearch,我们在通过Low和High序号得到Mid以后,应该如何剔除一半的数据呢?

下面是rotate后的一个有序数组的图。四边形的斜边表示数组中数值的大小。

在这种情况下数组分了两部分,分别都是有序(递增)的。

当我们计算了Mid以后,有两种可能,分别用Mid1和Mid2表示。

1. 如果A[Low] < A[Mid],说明Mid落在区间1中,即图中Mid1的位置。那么,如果target小于A[Mid1],那么继续在Low和Mid1中间搜索;否则,在Mid1和High中间搜索;

2. 如果A[Low] >= A[Mid],说明Mid落在区间2中,即图中Mid2的位置。同理,如果target小于A[Mid2],那么继续在Low和Mid2中间搜索;否则,在Mid2和High中间搜索。

这样,平均地,我们每次剔除一半数据,时间复杂度是O(logn)。

代码如下:

 1 private static int search2(int[] A, int target){
 2         int lo = 0;
 3         int hi = A.length - 1;
 4         while(lo <= hi){
 5             int mid = lo + (hi - lo)/2;
 6             if(target == A[mid]) return mid;
 7             if(A[mid] > lo){
 8                 if(target >= lo && target < A[mid]){
 9                     hi = mid - 1;
10                 }else {
11                     lo = mid + 1;
12                 }
13             }else {
14                 if(target <= hi && target > A[mid]){
15                     lo = mid + 1;
16                 }else {
17                     hi = mid -1;
18                 }
19             }
20         }
21         return -1;
22     }
View Code

 

 

posted on 2013-07-07 17:39  lichen782  阅读(2195)  评论(4编辑  收藏  举报