【Leetcode刷题足迹day1】704二分查找 27移除元素

题目

704
给定一个 n 个元素有序的(升序)整型数组 nums 和一个目标值 target ,写一个函数搜索 nums 中的 target,如果目标值存在返回下标,否则返回 -1

思路

这道题的前提是:

  • 数组为有序数组
  • 数组中无重复元素,因为一旦有重复元素,使用二分查找法返回的元素下标可能不是唯一的

二分法易错点

  • while循环里面
  • if条件里面

需要区别 [left, right], [left, right), 区间的定义就是不变量,再二分查找的过程中保持不变量,换句话说就是 在循环结束前, 每次循环的开始都要保证这次开始的区间和原来的区间形式一致。

两种写法

[left, right]

left = 0
right = num.size - 1

while(left <= right): #是合法区间, 例如[1,1]中只有一个元素 1, 是合法的
	middle = (left +right)/2 
	# 这里可以使用 middle = left + (right - left)/2 用以防止越界
	if (num[middle] > target):
		right = middle - 1 
		# 因为既然num[middle] 都已经确定大于 target,那么num[middle]必不是需要的数
		#如果这里是 right = middle, 那么相当于把一个已经排除在外的数值再次作为了下一轮排查的边界,那么这个边界处理一定是有问题的
	else if (num[middle] < target):
		left = middle + 1
	else return middle
return -1

[left, right)

left = 0
right = num.size

while(left < right): #因为在区间定义中 right值根本取不到
	middle = (left + right)/2 
	# 这里可以使用 middle = left + (right - left)/2 用以防止越界
	if (num[middle] > target):
		right = middle 
		# 这里相当于需要不断继承最开始的开区间,所以需要一个取不到得值
	else if (num[middle] < target):
		left = middle + 1
		#这里是闭区间所以还是要+1
	else return middle
return -1

tips据观察来说,可以优先使用左闭右开的方法,在执行用时差不多的情况下,内存消耗会小一些


题目

27
给你一个数组 nums 和一个值 val,你需要 原地移除所有数值等于 val 的元素,并返回移除后数组的新长度。

不要使用额外的数组空间,你必须仅使用 O(1) 额外空间并原地修改输入数组。

元素的顺序可以改变。你不需要考虑数组中超出新长度后面的元素。

示例 1:

输入:nums = [3,2,2,3], val = 3
输出:2, nums = [2,2]
解释:函数应该返回新的长度 2, 并且 nums 中的前两个元素均为 2。你不需要考虑数组中超出新长度后面的元素。例如,函数返回的新长度为 2 ,而 nums = [2,2,3,3] 或 nums = [2,2,0,0],也会被视作正确答案。

示例 2:

输入:nums = [0,1,2,2,3,0,4,2], val = 2
输出:5, nums = [0,1,4,0,3]
解释:函数应该返回新的长度 5, 并且 nums 中的前五个元素为 0, 1, 3, 0, 4。注意这五个元素可为任意顺序。你不需要考虑数组中超出新长度后面的元素。

思路

  • 对数组底层实现的理解:连续的相同类型元素的集合
  • 数组中的元素不能删除只能覆盖
  • 删掉之后其实数组的内存空间还是没有变,各个编程语言会将其包装
  • O(n)操作

暴力解法

双层for循环

#时间复杂度 O(n^2)
#空间复杂度 O(1)
size = nums.size()
for i in range(0,nums.size):
	if nums[i] == val: #发现需要移除得元素就将之后的数组全部前移一位
		for j in range(i+1, nums.size):
			nums[j-1] = nums[j] 
		i-- #因为下表i之后的数值都向前移动了一位,所以i也向前移动一位
		size-- #此时的数组大小-1
return size

双指针

动图演示

使用已成for循环做两层for循环的事

#时间复杂度:O(n)
#空间复杂度:O(1)
#fast 快指针 新数组中所需要的元素
#slow 慢指针 新数组中元素的下标值

slow = 0
for fast in range(0,nums.size):
	if(nums[fast] != val):
		nums[slow] = nums[fast]
		slow++
return slow+1 #就是新数组的大小

整个过程相当于对数组重新赋值,也就是谈到的覆盖操作,当遇到不是要求删除的值的时候就把它放到原来的位置或者较原来靠前的位置(因为是删除,所以留下的数的位置必定是不变或者提前的)慢指针所代表的就是新数组的下标,这里完全等于一个新数组n[i]中的i

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 1
    评论
<h3>回答1:</h3><br/>1. 首先,你需要在VS Code中安装LeetCode插件。打开VS Code,点击左侧的“扩展”图标,搜索“LeetCode”,然后点击“安装”按钮。 2. 安装完成后,你需要登录你的LeetCode账号。点击左侧的“LeetCode”图标,然后点击“登录”按钮。输入你的LeetCode账号和密码,然后点击“登录”按钮。 3. 登录成功后,你可以开始刷题了。点击左侧的“LeetCode”图标,然后点击“题库”按钮。在题库中选择你想要刷的题目,然后点击“开始”按钮。 4. 在刷题过程中,你可以使用VS Code提供的一些功能,比如自动补全、代码提示、代码格式化等。这些功能可以帮助你更快地完成题目。 5. 刷完题目后,你可以提交你的代码并查看测试结果。点击左侧的“LeetCode”图标,然后点击“提交”按钮。输入你的代码,然后点击“提交”按钮。稍等片刻,你就可以看到测试结果了。 总之,使用VS Code安装LeetCode插件刷题非常方便,可以帮助你更快地提高算法能力。 <h3>回答2:</h3><br/>VS Code是一个很流行的开发工具,LeetCode是很多程序员用来刷算法题的平台。在VS Code中安装LeetCode插件可以提供更好的刷题体验,还可以方便地保存和管理自己的代码。 下面是以Windows系统为例介绍在VS Code中安装LeetCode插件的步骤: 第一步:安装VS Code 在官网下载安装VS Code,https://code.visualstudio.com/ 第二步:打开Extensions标签 点击左侧菜单栏中的Extensions标签,在搜索框中输入“LeetCode”。 第三步:安装LeetCode插件 在搜索结果中,找到LeetCode插件并点击“Install”安装。 第四步:配置LeetCode插件 安装完毕后,配置LeetCode插件。点击左侧菜单栏中的“LeetCode”标签,根据提示进行配置。 第五步:使用LeetCode插件 在左侧菜单栏中的“LeetCode”标签下,点击“Problems”即可进入刷题页面。 总结:安装LeetCode插件可以为刷题提供更好的开发环境和代码管理工具,操作简便,适合程序员们使用。 <h3>回答3:</h3><br/>VSCode是一款功能强大的代码编辑器,不仅支持多种编程语言,还能通过插件进行扩展,其中包括LeetCode刷题插件。安装LeetCode插件,可以大大提升刷题效率和舒适度。安装LeetCode插件,大致可以分为以下几个步骤: 1. 安装VSCode:首先需要下载并安装VSCode,可以从官网(https://code.visualstudio.com/)获取。 2. 安装LeetCode插件:在VSCode中打开“扩展”选项卡,搜索“LeetCode”,找到对应的插件,点击“安装”。 3. 配置LeetCode插件:在VSCode中点击左下角的“LeetCode插件设置”按钮,进入插件的配置页面。在这里可以设置LeetCode的默认语言、代码保存目录、登录账号等信息。 4. 登录LeetCode账号:在配置页面中设置好账号信息后,可以点击登录按钮,跳转到LeetCode的官网,进行账号登录。 5. 开始刷题:在LeetCode插件的“输入问题编号”处输入题目编号,点击“搜索”即可进入题目页面,进行刷题操作。LeetCode插件还提供了多种题目操作,如代码提交、答案对比、题目复制等功能,可根据需求进行使用。 总之,安装LeetCode插件需要一些简单的操作步骤和注意事项,但对于提高刷题效率来说是非常方便实用的。

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

ChenSuperstar

你的鼓励将是我创作的最大动力

¥2 ¥4 ¥6 ¥10 ¥20
输入1-500的整数
余额支付 (余额:-- )
扫码支付
扫码支付:¥2
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值