在有序旋轉陣列中找到乙個數
有序陣列arr可能經過一次旋轉處理,也可能沒有,且arr可能存在重複的數。例如,有序陣列[1, 2, 3, 4, 5, 6, 7],可以旋轉處理成[4, 5, 6, 7, 1, 2, 3]等。給定乙個可能旋轉過的有序陣列arr,再給定乙個數num,返回arr中是否含有num
關於旋轉操作:可以簡單的理解為把序列從某個位置切成兩段然後交換位置
[要求]
期望複雜度為o
(logn
)o(\log n)
o(logn)
輸入描述:
第一行兩個整數n, num。分別表示陣列大小, 需要找的數。
接下來一行n個整數表示陣列內的數。
輸出描述:
若num存在於陣列中,輸出"yes",否則輸出"no"
示例1輸入
7 7
4 5 6 7 1 2 3
輸出yes
示例2
輸入
7 998244353
4 5 6 7 1 2 3
輸出no
備註:
1 ⩽n
⩽105
1 \leqslant n \leqslant 10^5
1⩽n⩽1051⩽
arri
⩽109
1 \leqslant arr_i \leqslant 10^9
1⩽arri
⩽10
9解法一(兩次二分):
參考 在有序旋轉陣列中找到最小值 一題,如果我們可以找到分界點,就可以確定 num 在左右哪個區間,然後直接在該區間上進行正常的二分查詢即可。
把複雜問題分解成簡單的子問題思想很重要。
解法一**:
#include
using
namespace std;
const
int n =
100000
;int n, k;
int a[n]
;int
main
(void
)int l =
0, r = n, m;
if( a[n]
< a[0]
)if( k <= a[n]
) r = n;
else l =0,
--r;
}while
( l < r )
if( a[m]
> k ) r = m;
else l = m +1;
}puts
( a[r]
== k ?
"yes"
:"no");
return0;
}
解法二(一次二分):
還是參考 在有序旋轉陣列中找到最小值 。我們可以在二分過程中,通過一些條件判斷 num 在哪個區間:
解法二**:
#include
using
namespace std;
const
int n =
100000
;int n, k;
int a[n]
;int
main
(void
)int l =
0, r = n, m;
while
( l < r )
if( a[m]
>= a[0]
)else
}puts
( a[r]
== k ?
"yes"
:"no");
return0;
}
在有序旋轉陣列中找到乙個數
題目 有序陣列arr可能經過一次旋轉處理,也可能沒有,且arr可能存在重複的數。例如,有序陣列 1,2,3,4,5,6,7 可以旋轉處理成 4,5,6,7,1,2,3 等。給定乙個可能旋轉過的有序陣列arr,再給定乙個數num,返回arr中是否含有num。public class getnum in...
在有序旋轉陣列中找到最小值
題目 有序陣列arr可能經過一次旋轉處理,也可能沒有,且arr可能存在重複的數。例如,有序陣列 1,2,3,4,5,6,7 可以旋轉處理成 4,5,6,7,1,2,3 等。給定乙個可能旋轉過的有序陣列arr,返回arr中的最小值。基本思路 盡可能的利用二分查詢,但是最壞情況仍然無法避免o n 的時間...
在有序旋轉陣列中找到最小值
在有序旋轉陣列中找到最小值 有序陣列arr可能經過一次旋轉處理,也可能沒有,且arr可能存在重複的數。例如,有序陣列 1,2,3,4,5,6,7 可以旋轉處理成 4,5,6,7,1,2,3 等。給定乙個可能旋轉過的有序陣列arr,返回arr中的最小值。要求 期望複雜度為o log n o log n...