leetcode33. 搜索旋转排序数组
假设按照升序排序的数组在预先未知的某个点上进行了旋转。
( 例如,数组 [0,1,2,4,5,6,7] 可能变为 [4,5,6,7,0,1,2] )。
搜索一个给定的目标值,如果数组中存在这个目标值,则返回它的索引,否则返回 -1 。
你可以假设数组中不存在重复的元素。
你的算法时间复杂度必须是 O(log n) 级别。
示例 1:
输入: nums = [4,5,6,7,0,1,2], target = 0
输出: 4
分析:
func search(nums []int, target int) int {
left := 0
right := len(nums) - 1
for left <= right {
mid := (left + right) / 2
if nums[mid] == target {
return mid
}
// 判断是否在前半部分查找
//target在left和mid中间,右索引前移
//mid小于right,并且target小于mid,即target在mid左边,右索引前移
//mid小于right,并且target大于right,有旋转
if (nums[left] <= target && target <= nums[mid]) || (nums[mid] <= nums[right] && (target < nums[mid] || target > nums[right])) {
right = mid - 1
} else {
left = mid + 1
}
}
return -1
}
面试题11. 旋转数组的最小数字
把一个数组最开始的若干个元素搬到数组的末尾,我们称之为数组的旋转。输入一个递增排序的数组的一个旋转,输出旋转数组的最小元素。例如,数组 [3,4,5,1,2] 为 [1,2,3,4,5] 的一个旋转,该数组的最小值为1。
示例 1:
输入:[3,4,5,1,2]
输出:1
示例 2:
输入:[2,2,2,0,1]
输出:0
func minArray(numbers []int) int {
left := 0
right := len(numbers) - 1
middle := 0
for numbers[left] >= numbers[right] {
if right-left == 1 {
middle = right
break
}
middle = (left + right) / 2
if numbers[left] == numbers[middle] && numbers[right] == numbers[middle] {
return inOrder(numbers, left, right)
}
if numbers[middle] >= numbers[left] {
left = middle
} else if numbers[middle] <= numbers[right] {
right = middle
}
}
return numbers[middle]
}
func inOrder(numbers []int, left, right int) int {
result := numbers[left]
for i := left + 1; i < right; i++ {
if numbers[i] < result {
result = numbers[i]
}
}
return result
}