【面试题53-I 在排序数组中查找数字】
排序数组中的搜索问题,首先想到二分法。
面试题53-I:在排序数组中查找数字 I:统计一个数字在排序数组中出现的次数。
思路:由于是已排序数组,可以用二分查找找到我们的目标元素,但找到的位置不一定,可能前后都有相同的数字。然后再用双指针 i
和 j
分别指向找到的元素位置两侧,判断是否等于 target
,若相等则计数器加 1,并移动指针。
class Solution:
def search(self, nums: List[int], target: int) -> int:
if not nums: return 0
n = len(nums)
idx = self.biSearch(nums, target, 0, n-1)
if idx is not None:
count = 1
i, j = idx - 1, idx + 1
while i >= 0 and nums[i] == target:
count += 1
i -= 1
while j < n and nums[j] == target:
count += 1
j += 1
return count
return 0
def biSearch(self, nums, target, low, high):
n = len(nums)
while low >= 0 and high < n and low <= high:
mid = int((low + high) / 2) # 向下取整
if nums[mid] == target:
return mid
elif nums[mid] > target:
high = mid - 1
else:
low = mid + 1
return None
【面试题53-II 0~n-1中缺失的数字】
面试题53-II:0~n-1中缺失的数字:一个长度为n-1的递增排序数组中的所有数字都是唯一的,并且每个数字都在范围0~n-1之内。在范围0~n-1内的n个数字中有且只有一个数字不在该数组中,请找出这个数字。
思路 1:由于题目条件限定了数组递增、长度为 n-1,且每个数字都在 0~n-1 范围内,容易知道实际上这个数组就是从 0 开始的,直接循环判断数组元素下标和元素本身是否对应,出现不对应的就是缺失的数字,如果是缺失了最后一个数字,直接返回数组长度即可。
时间复杂度:O(n)
class Solution:
def missingNumber(self, nums: List[int]) -> int:
if not nums: return 0
n = len(nums)
for i in range(n):
if nums[i] != i:
return i
return n
思路 2:使用二分法,只不过查找条件不是具体的某个数,而是数组下标是否与数组元素相等。若相等说明缺失的数字在后半段,否则就在前半段。
时间复杂度:O(logn),二分法为对数级别的复杂度
class Solution:
def missingNumber(self, nums: List[int]) -> int:
if not nums: return 0
low, high = 0, len(nums)-1
while low <= high:
mid = int((low + high) / 2)
if nums[mid] == mid: low = mid + 1
else: high = mid - 1
return low