Problem 29:Divide Two Integers

  不使用除法、乘法和求余运算,完成两个数的除法,当数值溢出时,返回MAX_INT

  解题思路:第一想法,直接用被除数循环减去除数,每次减得的结果大于0,则结果加1,小于0时循环结束。解法没问题,但是复杂度太高,当用一个很大的数去除一个很小的数时,会超时。
  于是我们想到,我每次不是减去除数,而是依次减去除数的2的指数次幂倍,一直看能减到多少结果小于0,然后我们记录这个是2的多少倍,并对剩余值,继续重复这个操作:
  譬如13除以4,13>4,4<<1为8;13>8,8<<1为16;13<16,记录res=2=4,剩余13-8=7,然后将7看做13,重复操作。
注意越界操作的处理。

  def divide(self, dividend, divisor):""":type dividend: int:type divisor: int:rtype: int"""sign = (dividend > 0) == (divisor > 0)dividend = abs(dividend)divisor = abs(divisor)res = 0while dividend >= divisor:t, c = divisor, 1while dividend >= t:t <<= 1c <<= 1t >>= 1c >>= 1dividend -= tres += cif not sign:res = - resreturn min(max(res, -2147483648),2147483647)

Problem 33:Search in Rotated Sorted Array

  在一个rotated过的排序数组中,找到target值的下标,如果不存在。返回-1,譬如一个排血数组[1,2,3,4,5,6,7],rotated过后可能变成[5,6,7,1,2,3,4],数组中没有重复元素

  解题思路:很明显,这题是要用类似二分查找的方法,得到一个O(logN)的解法,不同于在排序数组中找,我们的判断条件要稍微复杂一点,因为他们可能不在一个单调区间。
  考虑数组[4,6,7,0,1,2,3],l=0,r=6,target为6,此时nums[mid]=0<6,按照为旋转之前的话,l应该更新为3,但是在这显然不成立。我们分情况讨论:

  • 当num[0]>target,此时,target只可能出现在旋转后的部分,即上述例子的…0,1,2,3部分,如果此时num[0]<num[mid],代表mid之前仍未旋转(此时target一定是小于num[mid]的),因此l要更新为mid+1;如果此时num[0]> num[mid],代表mid之前已经旋转,如果target>num[mid],l要更新为mid+1,否则,r=mid
  • 当num[0]<target时同理

    综上,我们发现,l需要被更新为mid+1的时候,共有如下情况:

  • num[0]>target and num[0]<num[mid] and target<num[mid]

  • num[0]>target and num[0]>num[mid] and target>num[mid]
  • num[0]<target and num[0]<num[mid] and target>num[mid]

即,上述三个条件的异或为True的时候,更新l=mid+1,否则更新r=mid
其实,三个条件的排列组合共有8种,其中三种是更新l=mid+1的,三种更新r=mid的,还有两种是不存在的情况。

  def search(self, nums, target):""":type nums: List[int]:type target: int:rtype: int"""l, r = 0, len(nums) - 1while l < r:mid = (l + r) / 2if (nums[0] > target) ^ (nums[0] > nums[mid]) ^ (target > nums[mid]):l = mid + 1else:r = midreturn l if target in nums[l:l+1] else -1

Problem 34:Search for a Range

  给定一个升序排列的数字,找到target出现的区间,如果没有,返回[-1,-1],譬如[1,2,3,4,6,6,8],target=6,则返回[4,5],要求时间复杂度为O(logn)

  解题思路:(心累,之前写了没保存了,这里就大概说一下吧)时间复杂度要求为二分查找,依次找到左右边界,按照下述二分查找的策略,最终得到的结果一定是左边界(如果target存在的话),查找右边界的方式同理,只需将下述策略的所有l和r互换之后看即可:即l=mid+1,替换为r=mid-1;r=mid替换为l=mid
查找左边界

    l,r = 0, len(nums)-1while l < r:mid = (l + r) //2if target > nums[mid]:l = mid + 1           else:r = mid

  l和r即是左边界
查找右边界

    l,r = l, len(nums)-1while l < r:mid = (l + r + 1)//2if target < nums[mid]:r = mid - 1else:l = mid

  此处的l和r即是左边界,需要注意的是求mid的加1操作,因为整除会向下取整,因此查找左边的最后一次循环,l是不动的,由r向l靠拢,求解右边界的时候正好相反,我们需要r不动,l向r靠拢,因此需要加1。


Problem 36:Valid Sudoku

  给定一个初始化的数独棋盘,判断是否有效,即每个数字在每一行、每一列和每一个3*3的单元内是否只出现了一次,没有被填充的单元值为’.’

  解题思路:(心累,之前写了没保存了,这里就大概说一下吧)开始理解错,其实只用遍历棋盘,记录每个数字出现的位置(‘.’的不用管),遍历结束后判断是否满足要求即可,python一行搞定

    def isValidSudoku(self, board):""":type board: List[List[str]]:rtype: bool"""pos = sum(([(d, r), (c, d), (d, r/3, c/3)] for r, row in enumerate(board) for c, d in enumerate(row) if d != '.'), [])return len(pos) == len(set(pos))

  注意,前两个二元组不能写成(d,r),(d,c)不然无法标识行还是列


LeetCode刷题之路(四)——medium的进阶相关推荐

  1. LeetCode 刷题之路(python版)

    摘自:https://blog.csdn.net/qq_32384313/article/details/90745354 LeetCode 刷题之路(python版) 小坏wz 2019-06-02 ...

  2. LeetCode刷题(十)----数组-----medium部分(Java、C++)

    LeetCode刷题(十)-----数组-------medium部分(Java.C++) 238. 除自身以外数组的乘积 给定长度为n的整数数组nums,其中n>1,返回输出数组output, ...

  3. python -- leetcode 刷题之路

    第一题 给定一个整数数组和一个目标值,找出数组中和为目标值的两个数. 你可以假设每个输入只对应一种答案,且同样的元素不能被重复利用. 示例: 给定 nums = [2, 7, 11, 15], tar ...

  4. LeetCode刷题——消除游戏#390#Medium

    消除游戏的思路探讨与源码     消除游戏的题目如下图,该题属于递归类和数学类型的题目,主要考察对于数学方法的使用和递归方法的理解.本文的题目作者想到2种方法,分别是递归方法和数学模拟方法,其中递归方 ...

  5. LeetCode刷题——建立四叉树#427#Medium

    建立四叉树的思路探讨与源码     建立四叉树的题目如下图,该题属于树类和数组类型的题目,主要考察对于搜索方法的使用和树结构的理解.本文的题目作者想到2种方法,分别是递归方法和二维前缀和方法,其中递归 ...

  6. leetcode 刷题之路 64 Construct Binary Tree from Inorder and Postorder Traversal

    Given inorder and postorder traversal of a tree, construct the binary tree. Note: You may assume tha ...

  7. #leetcode刷题之路35-搜索插入位置

    给定一个排序数组和一个目标值,在数组中找到目标值,并返回其索引.如果目标值不存在于数组中,返回它将会被按顺序插入的位置. 你可以假设数组中无重复元素. 示例 1: 输入: [1,3,5,6], 5 输 ...

  8. #leetcode刷题之路39-组合总和

    给定一个无重复元素的数组 candidates 和一个目标数 target ,找出 candidates 中所有可以使数字和为 target 的组合. candidates 中的数字可以无限制重复被选 ...

  9. LeetCode刷题之路:1049. 最后一块石头的重量 II

    有一堆石头,用整数数组 stones 表示.其中 stones[i] 表示第 i 块石头的重量. 每一回合,从中选出任意两块石头,然后将它们一起粉碎.假设石头的重量分别为 x 和 y,且 x < ...

最新文章

  1. struts2中使用json遇到的问题总结及示例程序
  2. 控件属性、事件持久化
  3. java8之前_Java 8 之前的时间处理
  4. 哈希扩展长度攻击_哈希长度扩展攻击
  5. Linux解压tar.gz、zip、tar.bz2 文件与对应的命令
  6. LeetCode 61. 旋转链表(python、c++)
  7. python统计英文单词个数_python统计英文文本中的回文单词数
  8. nyoj349 poj1094 Sorting It All Out(拓扑排序)
  9. JAVA生成(可执行)Jar包的全面详解说明 [打包][SpringBoot][Eclipse][IDEA][Maven][Gradle][分离][可执行]...
  10. php和js封装函数,介绍javascript-ecma中的几种封装函数
  11. Linux C 语言 Socket 通信(多对多)多线程实现
  12. 注册表怎么禁用计算机,如何禁用注册表,注册表禁用和启动的方法
  13. xp系统蓝屏代码7b_电脑开机蓝屏错误代码0x0000007B的详细解决过程
  14. poj2249Binomial Showdown
  15. 使用vuepress-reco主题创建博客
  16. iOS —label自动换行
  17. 前后坐人书柜书桌的标准做法
  18. TalkingData游戏统计IOS工程 出现TDGAOnEvent 报错的问题
  19. ae 创建图像等高线 蒙版_「PS软件」工具使用,图层蒙版与橡皮擦的应用分析
  20. 香港科大2020年TOP12人气热帖@商学院公众号

热门文章

  1. U.K. Considers Giving RBS Bailout Leeway
  2. java中如何定义接口_java中如何定义一个接口
  3. 【C语言】-- 整型数据的存储
  4. select 1 from和exists
  5. 科技筑梦创新成长 “探知未来”一直在路上
  6. 过度在意别人的看法,是因为缺少自我
  7. 激光器仿真:(7)半导体+波导混合锁模激光器
  8. Python 下标异常
  9. 阿里云计算重磅公布云原生裸金属方法:裸金属+容器,此方法解锁云计算的新方式
  10. cdc有哪些rapper_cdc说唱会馆成员介绍