二分查找解题模板

所谓模板只是为了在解决相关问题时提供一个较好的出发点,具体细节还应根据具体的题目进行调整。

二分查找模板

二分查找在解题过程中经常出现,如查找target是否在给定的数组中存在、查找包含重复元素的数组中某一个数target对应的左右边界或查找旋转数组的旋转点……相比较于线性扫描O(N)O(N)的实际复杂度,二分查找的时间度为O(logN)O(\log N)


查找target在nums中是否存在?


[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-5XpurHQC-1585468940179)(C:\Users\dyliang\AppData\Roaming\Typora\typora-user-images\image-2020032915563423

 def binarySearch(nums, target):
      left = 0
      right = len(nums) - 1

      while left <= right:
          mid = left + (right - left) // 2
          if nums[mid] == target:
              return mid
          elif nums[mid] < target:
              left = mid + 1
          elif self.nums[mid] > target:
              right = mid - 1
      
      return -1

查找target在nums中的左边界


在这里插入图片描述

 def findLeftBound(nums, target):
      left = 0
      right = len(nums) - 1

      while left <= right:
          mid = left + (right - left) // 2
          if nums[mid] == target:
              right = mid - 1
          elif nums[mid] < target:
              left = mid + 1
          elif nums[mid] > target:
              right = mid - 1
              
return left if left <= len(nums)-1 and nums[left] == target else -1

查找target在nums中的右边界


在这里插入图片描述

def findRightBound(nums, target):
      left = 0
      right = len(nums) - 1

      while left <= right:
          mid = left + (right - left) // 2
          if nums[mid] == target:
              left = mid + 1
          elif nums[mid] < target:
              left = mid + 1
          elif nums[mid] > target:
              right = mid - 1

      return right if right >= 0 or nums[right] == target else -1 

完整测试模板

class BinarySearch:
    def __init__(self, nums, target):
        self.nums = nums
        self.target = target


    def binarySearch(self):
        left = 0
        right = len(self.nums) - 1

        while left <= right:
            mid = left + (right - left) // 2
            if self.nums[mid] == self.target:
                return mid
            elif self.nums[mid] < self.target:
                left = mid + 1
            elif self.nums[mid] > self.target:
                right = mid - 1
        
        return -1

    def findLeftBound(self):
        left = 0
        right = len(self.nums) - 1

        while left <= right:
            mid = left + (right - left) // 2
            if self.nums[mid] == self.target:
                right = mid - 1
            elif self.nums[mid] < self.target:
                left = mid + 1
            elif self.nums[mid] > self.target:
                right = mid - 1

        return left if left <= len(self.nums)-1 and self.nums[left] == self.target else -1


    def findRightBound(self):
        left = 0
        right = len(self.nums) - 1

        while left <= right:
            mid = left + (right - left) // 2
            if self.nums[mid] == self.target:
                left = mid + 1
            elif self.nums[mid] < self.target:
                left = mid + 1
            elif self.nums[mid] > self.target:
                right = mid - 1

        return right if right >= 0 or self.nums[right] == self.target else -1 

 
if __name__ == "__main__":
    # 简单二分查找
    # nums = [1,2,3,4,5,6]
    # target = 2
    # bs = BinarySearch(nums, target)
    # print (bs.binarySearch())
	
    # 查找左边界
    # nums = [1,2,2,2,3,4]
    # target = 2
    # bs = BinarySearch(nums, target)
    # print (bs.findLeftBound())
	
    # 查找右边界
    nums = [1,2,2,2,3,4]
    target = 2
    bs = BinarySearch(nums, target)
    print (bs.findRightBound())

关于更多如边界条件的设置等关键坑详读二分查找解题套路框架,强推!

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章