283.移动零 关于列表list与remove原理*****(简单)
题目:
给定一个数组 nums,编写一个函数将所有 0 移动到数组的末尾,同时保持非零元素的相对顺序。
注意,该题目要求不开辟行的数组空间,在原数据上进行操作。
示例:
输入:[0,1,0,3,12]
输出:[1,3,12,0,0]
说明:
- 必须在原数组上操作,不能拷贝额外的数组。
- 尽量减少操作次数。
自我解答:
思路1:如同冒泡算法那样,用两个for循环进行遍历,将0依次移动到列表最后面。
缺点:复杂度太高,n^n,上传答案时会报错。
思路2:for循环遍历数组,当该数为0时,remove移除该数,
在这里有两个python知识点。
原本,我是希望先把所有的0删除后,再往后面添加同样数量的0,但是,发现删不掉0的情况
list1 = [0,2,0,0,8,0,8,0,1]
class Solution2:
def moveZeroes(self, nums):
for i in nums:
if i ==0:
nums.remove(i)
# nums.append(0)
print(nums) s = Solution2()
s.moveZeroes(list1)
#[2, 8, 8, 0, 1]
百度了一番发现了其中的奥秘:
for循环原理
python中for循环是遍历所有nums下标,然后根据下标遍历列表。
当列表边遍历边删除的时候,会出现漏遍历的情况,当列表中的数字被删除时,后面的数字会跟上,他们的下标也会跟着改变,如
list1=[1,2,3,4,5,6]
for i in list1:
remove(i)
#[2,4,6]
因为删除了1,所以2代替了原来1的位置,for循环就会寻找现在列表中的2位置是谁,很显然2是数字3.
但是又有一个问题,难道在遍历了6之后还有3个下标没有遍历会怎么处理呢。
这就涉及到for循环的内部原理,其中有__next__方法就是获取下一个元素,当获取不到时就会报错,然后内部处理异常,停止取值。
remove原理
但光是这样的话,上述代码最后执行的结果不就是[2,0,8,8,0,1]吗。
原来remove的删除原因是删除当前列表中第一个匹配的值,所以当遍历到后面的0时会删除前面跳过的0,但是遍历到的0总是比较少的,所以最后总会漏掉1到2个。
解决方法:
1.这个方法不是很完美,因为方法不变,只是边删除0边在后面添加0,这就使得原先没有遍历结束的下标全部遍历,所以不妨换一个角度想。
我们每遍历到一个0就获得删除一个0的机会(remove),每删除一个0就会添加一个0,所以列表总长度不变,最后原先列表遍历结束后,就会遍历添加进去的0,直到遍历结束。
或者理解为保证列表长度不变的情况下,尽可能的删掉队列中所有的0,那这些0到哪里去了呢,显然就是append的哪些:
list1 = [0,2,0,0,8,0,8,0,1]
class Solution2:
def moveZeroes(self, nums):
for i in nums:
if i ==0:
nums.remove(i)
nums.append(0)
print(nums)
#[2, 8, 8, 1, 0, 0, 0, 0, 0]
2,从后往遍历。
这种方法适用于任何边循环边改变列表元素的问题,使用切片中默认值的方式:
class Solution:
def moveZeroes(self, nums: List[int]) -> None:
for i in nums[::-1]:
if i==0:
nums.remove(i)
nums.append(0)
添加的0和剔除的0在总列表的最后,不会影响for循环中即将遍历的值.
官方解答:
这个题目的标签是数组与双指针。可以这么做:
定义一个长指针和一个短指针。
长指针用来判断列表中的0元素直到最后,短指针则用来记录非0的值到列表中。
最后再在短指针的最后将所有的值改成0,实现该功能。
list1 = [0,2,0,0,8,0,8,0,1]
class Solution:
def moveZeroes(self, nums):
long_t = 0
short_t = 0
while long_t < len(nums):
if nums[long_t]!=0:
nums[short_t] = nums[long_t]
long_t +=1
short_t +=1
else:
long_t +=1
while short_t <len(nums):
nums[short_t] = 0
short_t += 1
print(nums) #[2, 8, 8, 1, 0, 0, 0, 0, 0]
python中实现指向数组的指针都可以使用这种方法,这种方法在执行时间的角度来讲也比较合理。
283.移动零 关于列表list与remove原理*****(简单)的更多相关文章
- 前端与算法 leetcode 283. 移动零
目录 # 前端与算法 leetcode 283. 移动零 题目描述 概要 提示 解析 解法一:暴力法 解法二:双指针法 算法 传入[0,1,0,3,12]的运行结果 执行结果 GitHub仓库 # 前 ...
- 【Leetcode】【简单】【283. 移动零】【JavaScript】
题目描述 283. 移动零 给定一个数组 nums,编写一个函数将所有 0 移动到数组的末尾,同时保持非零元素的相对顺序. 示例: 输入: [0,1,0,3,12]输出: [1,3,12,0,0] 说 ...
- 在Python的列表中利用remove()方法删除元素的教程
在Python的列表中利用remove()方法删除元素的教程 这篇文章主要介绍了在Python的列表中利用remove()方法删除元素的教程,是Python入门中的基础知识,注意其和pop()方法的区 ...
- Java实现 LeetCode 283 移动零
283. 移动零 给定一个数组 nums,编写一个函数将所有 0 移动到数组的末尾,同时保持非零元素的相对顺序. 示例: 输入: [0,1,0,3,12] 输出: [1,3,12,0,0] 说明: 必 ...
- 【LeetCode】283.移动零
283.移动零 知识点:数组:双指针: 题目描述 给定一个数组 nums,编写一个函数将所有 0 移动到数组的末尾,同时保持非零元素的相对顺序. 示例 输入: [0,1,0,3,12] 输出: [1, ...
- Android零基础入门第11节:简单几步带你飞,运行Android Studio工程
原文:Android零基础入门第11节:简单几步带你飞,运行Android Studio工程 之前讲过Eclipse环境下的Android虚拟设备的创建和使用,现在既然升级了Android Studi ...
- 1102: 零起点学算法09——继续练习简单的输入和计算(a-b)
1102: 零起点学算法09--继续练习简单的输入和计算(a-b) Time Limit: 1 Sec Memory Limit: 520 MB 64bit IO Format: %lldSub ...
- python(leetcode)-283移动零
给定一个数组 nums,编写一个函数将所有 0 移动到数组的末尾,同时保持非零元素的相对顺序. 示例: 输入: [0,1,0,3,12] 输出: [1,3,12,0,0] 说明: 必须在原数组上操作, ...
- LeetCode(283. 移动零)
问题描述 给定一个数组 nums,编写一个函数将所有 0 移动到数组的末尾,同时保持非零元素的相对顺序. 示例: 输入: [0,1,0,3,12] 输出: [1,3,12,0,0] 说明: 必须在原数 ...
随机推荐
- luoguP2480 [SDOI2010]古代猪文
题意 考虑所求即为:\(G^{\sum\limits_{d|n}C_n^d}\%999911659\). 发现系数很大,先用欧拉定理化简系数:\(G^{\sum\limits_{d|n}C_n^d\% ...
- Codeforces Round #552 (Div. 3) EFG(链表+set,dp,枚举公因数)
E https://codeforces.com/contest/1154/problem/E 题意 一个大小为n(1e6)的数组\(a[i]\)(n),两个人轮流选数,先找到当前数组中最大的数然后选 ...
- 开发者必备Linux命令
开发者必备Linux常用命令,掌握这些命令绝对够了,基于CenterOS7.6. 系统服务管理 systemctl 输出系统中各个服务的状态: systemctl list-units --type= ...
- [SpingBoot guides系列翻译]文件上传
文件上传 这节的任务是做一个文件上传服务. 概况 参考链接 原文 thymeleaf spring-mvc-flash-attributes @ControllerAdvice 你构建的内容 分两部分 ...
- Vue.js 源码分析(三十一) 高级应用 keep-alive 组件 详解
当使用is特性切换不同的组件时,每次都会重新生成组件Vue实例并生成对应的VNode进行渲染,这样是比较花费性能的,而且切换重新显示时数据又会初始化,例如: <!DOCTYPE html> ...
- Zookeeper 到底能帮我们解决哪些问题?
Zookeeper 从设计模式角度来看,是一个基于观察者模式设计的分布式服务管理框架,它负责存储和管理大家都关心的数据,然后接受观察者的注册,一旦这些数据的状态发生变化,Zookeeper 就将负责通 ...
- redis 面试问题问答Top 10
1)什么是Redis? English:Redis is an open source (BSD licensed), in-memory data structure store, used as ...
- JSP是Servlet详解
前言:前一段时间写了好多Servlet和JSP相关的博客,自以为理解的差不多了,岂不知人外有人,天外有天,代码外还有源码,受高人点拨,看了一下Servlet源码,感触颇深,再也不敢说懂了,不明白生活的 ...
- C#使用FileSystemWatcher来监控指定文件夹,并使用TCP/IP协议通过Socket发送到另外指定文件夹
项目需求: 局域网内有两台电脑,电脑A(Windows系统)主要是负责接收一些文件(远程桌面粘贴.FTP上传.文件夹共享等方式),希望能在A接收文件后自动传输到电脑B(Windows系统)来做一个备份 ...
- C++调用linux命令并获取返回值
qt中封装了相关的方法, 但是因为我的命令中用到了管道命令, 出现了非预期结果, 所有改用了linux系统原生的方法. 下边是一个判断某进程是否存在的例子. 当前存在一个问题,当linux返回多行时, ...