【leetcode】二分算法69、367、33

69. x 的平方根

class Solution:
    def mySqrt(self, x: int) -> int:
        # return int(x ** 0.5)
        # 直接用牛顿迭代法
        r = x
        while r * r > x:
            r = (r + x/r) // 2
        return int(r)

367. 有效的完全平方数

class Solution:
    def isPerfectSquare(self, num: int) -> bool:
        # 牛顿迭代法
        i = num 
        while i * i > num:
            i = (i + num/i) // 2
        return i* i == num

33. 搜索旋转排序数组

# 中间元素和左边界比较,使用左中位数
class Solution:
    def search(self, nums, target):
        size = len(nums)
        if size == 0:
            return -1
        left, right = 0, size - 1
        while left < right:
	    #注意,这里选用的是左中位数
            mid = left + (right-left)//2
            #左半部分有序
            if nums[left] < nums[mid]:
                if nums[left] <= target <= nums[mid]:
                    right = mid
                else:
                    left = mid + 1
            #右半部分有序
            else:
		#为了使这里left和right的更新和上面一样,所以使用nums[mid+1]
                if nums[mid+1] <= target <= nums[right]:
                    left = mid + 1 
                else:
                    right = mid
        # 后处理
        return left if nums[left] == target else -1
#  用异或来简化逻辑的过程
def search(self, nums, target):
    lo, hi = 0, len(nums) - 1
    while lo < hi:
        mid = (lo + hi) / 2
        if (nums[0] > target) ^ (nums[0] > nums[mid]) ^ (target > nums[mid]):
            lo = mid + 1
        else:
            hi = mid
    return lo if target in nums[lo:lo+1] else -1

74. 搜索二维矩阵

class Solution:
    def searchMatrix(self, matrix: List[List[int]], target: int) -> bool:
        if not matrix or not matrix[0]:
            return False
        left, right = 0, len(matrix) * len(matrix[0]) - 1
        array = [column for row in matrix for column in row]
        while left <= right:
            mid = ((right - left) >> 1) + left
            if array[mid] == target:
                return True
            elif array[mid] < target:
                left = mid + 1  
            else:
                right = mid - 1
        return False

参考的题解
153. 寻找旋转排序数组中的最小值

class Solution:
    def findMin(self, nums: List[int]) -> int:
        # 单调, 有界,有索引的时候采用二分查找的方法 
        lo, hi = 0, len(nums) - 1
        while lo < hi:
            mid = lo + (hi - lo) // 2 
            if nums[mid] > nums[hi]:
                lo = mid + 1 
            else:
                hi = mid
        return nums[lo]

你可能感兴趣的:(算法和数据结构刷题,笔记)