Search in Rotated Sorted Array (M)
題目
Suppose an array sorted in ascending order 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.
Your algorithm's runtime complexity must be in the order of O(log n).
Example 1:
Input: nums = [4,5,6,7,0,1,2], target = 0
Output: 4
Example 2:
Input: nums = [4,5,6,7,0,1,2], target = 0
Output: 4
題意
將一遞增數列的隨機后半部分與前半部分換位,得到新陣列,在新陣列中查找目標值,
思路
比較簡單的做法是先用一個二分找到兩個遞增序列的邊界,再用一個二分在對應的遞增序列里查找目標值,
也可以只用一個二分完成操作:求出mid,先考慮mid落在右遞增區間的情況,如果target也落在右遞增區間且比nums[mid]大,說明只需要繼續向右查找,令 left = mid + 1 即可,不然只要向左查找,令 right = mid - 1;同理,對于mid落在左遞增區間的情況進行處理,

代碼實作
Java
不求邊界
class Solution {
public int search(int[] nums, int target) {
int left = 0;
int right = nums.length - 1;
while (left <= right) {
int mid = (left + right) / 2;
if (nums[mid] == target) {
return mid;
}
// 通過與第一個值相比較來判斷mid落在左區間還是右區間
if (nums[mid] < nums[left]) {
if (target <= nums[right] && target > nums[mid]) {
left = mid + 1;
} else {
right = mid - 1;
}
} else {
if (target >= nums[left] && target < nums[mid]) {
right = mid - 1;
} else {
left = mid + 1;
}
}
}
return -1;
}
}
先求邊界
class Solution {
public int search(int[] nums, int target) {
if (nums.length == 0) {
return -1;
}
int left = 0;
int right = nums.length - 1;
int split = nums.length - 1; // 默認不存在邊界
while (left <= right) {
int mid = (left + right) / 2;
if (nums[mid] == target) {
return mid;
}
if (nums[mid] >= nums[left]) {
if (mid + 1 < nums.length && nums[mid + 1] < nums[mid]) {
split = mid;
break;
} else {
left = mid + 1;
}
} else {
if (mid - 1 >= 0 && nums[mid - 1] > nums[mid]) {
split = mid - 1;
break;
} else {
right = mid - 1;
}
}
}
// 選擇一個遞增區間進行二分查找
if (target >= nums[0]) {
return binarySearch(nums, 0, split, target);
} else {
return binarySearch(nums, split + 1, nums.length - 1, target);
}
}
private int binarySearch(int[] nums, int left, int right, int target) {
while (left <= right) {
int mid = (left + right) / 2;
if (target > nums[mid]) {
left = mid + 1;
} else if (target < nums[mid]) {
right = mid - 1;
} else {
return mid;
}
}
return -1;
}
}
JavaScript
/**
* @param {number[]} nums
* @param {number} target
* @return {number}
*/
var search = function (nums, target) {
let left = 0, right = nums.length - 1
while (left <= right) {
let mid = Math.trunc((right - left) / 2) + left
if (nums[mid] === target) {
return mid
}
if (target < nums[0] && nums[mid] >= nums[0]) {
left = mid + 1
} else if (target >= nums[0] && nums[mid] < nums[0]) {
right = mid - 1
} else if (nums[mid] < target) {
left = mid + 1
} else {
right = mid - 1
}
}
return -1
}
轉載請註明出處,本文鏈接:https://www.uj5u.com/qita/38859.html
標籤:其他
上一篇:vlan間互通的奇怪問題。
