微策略面試題:在旋轉後的陣列中查詢元素(二分查詢)

小飛_Xiaofei發表於2013-12-04

版權所有。所有權利保留。

歡迎轉載,轉載時請註明出處:

http://blog.csdn.net/xiaofei_it/article/details/17123303

一個無重複元素的有序陣列,經過若干次旋轉後,得到一個新陣列。比如[1,4,5,8,10,12,56,78]變成[12,56,78,1,4,5,8,10]。

現在要在這個陣列中尋找元素。

其實演算法很簡單,就是用二分查詢,只不過要看mid是屬於哪個部分(前半部分還是後半部分),因此有四種情況。

程式碼如下:

#include <iostream>
using namespace std;
int a[1000];
int find(int a[],int len,int x)
{
	int start=0,end=len-1,mid;
	while (start<=end)
	{
		mid=(start+end)/2;
		if (a[mid]==x)
			return mid;
		if (a[start]<a[mid])
		{
			if (a[mid]<x)
				start=mid+1;
			else
				end=mid-1;
		}
		else
		{
			if (a[mid]<x)
				end=mid-1;
			else
				start=mid+1;
		}
	}
	return -1;
}
int main()
{
	int n,x;
	while (cin>>n>>x)
	{
		for (int i=0;i<n;i++)
			cin>>a[i];
		cout<<find(a,n,x)<<endl;
	}
	return 0;
}

以上程式碼對輸入輸出的處理是模仿ACM的。n表示陣列元素個數,x表示要找的元素,然後n個數(保證無重複,並且是旋轉後的陣列)。

另外,說一下為什麼要無重複。如果有重複,就不能通過mid判斷屬於哪部分,要通過其他方法,這就不是簡單的二分查詢了,時間複雜度也不再是O(log n)了。

比如

3,3,3,5,3,3,3,3,3,3中找5

3,3,3,3,3,3,3,3,5,3中找5

3,3,3,1,3,3,3,3,3,3中找1

3,3,3,3,3,3,3,3,1,3中找1

相關文章