Day1 数组part1

Day1 数组part1

一、二分法

原理比较简单,高中知识——每次选取区间中间值,与目标值比较,依据比较结果更新区间边界,不断往复,最终得到目标值。

需要特别强调的是,二分法针对的数组必须是有序的!数组必须有序!

由于每次将数组长度折半,因此时间复杂度是O(logn),在长数组中查找具体的数值速度会很快。

对应题目参见Leetcode-704

在实际编写代码时,需要注意:

每次二分结束之后的子数组,需要在抽象的形式上和最开始的定义一致,以保证在while循环中的循环不变量,从而保证边界条件的准确判断,避免死循环。

具体而言,如果开始输入的数组是左闭右闭,那么每次更新之后,新的子数组区间边界也要保证左闭右闭,左闭右开亦然。

反映在代码上,左闭右闭需要在

  1. 开始时将右指针指向数组最右侧变量 left, right = 0, len(nums)-1
  2. 循环终止条件为left< =right,这是因为对于左闭右闭区间,左右边界相等是有意义的,此时只有一个数
  3. 在更新区间边界时,需要保证左闭右闭的一致性,即
    left = mid + 1
    right = mid -1
    

这样就保证:不管是对于原始输入,还是二分之后的子数组,在抽象形式上他们保持一致,均为左闭右闭,因此循环终止条件不会造成死循环。

此外,对于二分法,很多题目考察算法的终止状态。

步进debug推演就可以发现:左闭右闭算法最终状态是left和right指针重合,之后二者错开,跳出循环。

宏观上,两个指针在不断逼近目标数字,因此如果目标数字小于数组中的所有元素,那么终止状态是left和right指针重合的指向最左侧的最小元素,之后错开。

二、移除数组中的指定元素

直接的暴力想法是开辟新的空间,遍历所有数组元素,将非指定元素移动到新开辟的空间中

这是很自然的想法

但是如果要求不开辟新的存储空间,即原地的移除指定元素,这就需要使用双指针

原理也很好理解→fast指针遍历数组中的元素,看每次拿到的数是否等于 val,slow指针新数值的候选填充位置(待填充位置),将fast需要移动的数字(非移除数字),直接覆盖到slow的位置上,遇到需要移除的数字,fast向后移动,slow保持

对应题目参见Leetcode-27

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值