所有笔记内容参考廖雪峰官网,需要详细了解大家可以去这个网站,我这里主要做笔记方便自己复习
切片、迭代、列表生成式、生成器、迭代器
切片
主要功能是取list或者tuple中的部分元素
L=list(range(100))
M=L[0:3] #这条语句与Q=L[:3]一致
N=L[:3]
O=L[1:3]
P=L[-2:]
Q=L[-2:0] #这条语句与Q=L[-2:]一致
R=L[-3:-1]
S=L[:10:2]
T=L[::5]
U=L[:]
print('L[0:3]的输出结果是:',M)
print('L[:3]的输出结果是:',N)
print('L[1:3]的输出结果是:',O)
print('L[-2:]的输出结果是:',P)
print('L[-2:0]的输出结果是:',Q)
print('L[-3:-1]的输出结果是:',R)
print('L[:10:2]的输出结果是:',S)
print('L[::5]的输出结果是:',T)
print('L[:]的输出结果是:',U)
L[0:3]的输出结果是: [0, 1, 2]
L[:3]的输出结果是: [0, 1, 2]
L[1:3]的输出结果是: [1, 2]
L[-2:]的输出结果是: [98, 99]
L[-2:0]的输出结果是: []
L[-3:-1]的输出结果是: [97, 98]
L[:10:2]的输出结果是: [0, 2, 4, 6, 8]
L[::5]的输出结果是: [0, 5, 10, 15, 20, 25, 30, 35, 40, 45, 50, 55, 60, 65, 70, 75, 80, 85, 90, 95]
L[:]的输出结果是:[0…99]
分析:使用类似于L[a:b]
的语法可以取出下标为a到b-1的数
注意,倒数第一个元素的索引是-1
;
我们在使用L[-2:]
这种方式取倒数第二个到倒数第一个数的时候,不能使用L[-2:0]
这种语法,不知道是不是我电脑上的环境问题还是本身语法就不能那样写。
L[:10:2]
表示的是从前10个数中,每2个取一个
L[::5]
表示在L这个list中,每5个取一个
L[:]
表示直接复制原来的list
上面这些语法同样适用于tuple,只是tuple不可改变
迭代
Python中的for循环不仅用在list或者tuple上,还可以作用在其他可迭代对象上面,比如说dict就可以迭代:
d={'a':1,"b":2,"c":3}
for x in d:
print(x)
输出结果为
a
b
c
默认情况下,dict迭代的是key值,如果需要迭代value,可以用for x in d.values()
,如果需要同时迭代key和value,可以使用for k,v in d.items()
此外,字符串也是可迭代对象,因此可以作用于for循环:
for ch in 'ABC'
print(ch)
当我们使用for循环时,只要作用于一个可迭代对象,for循环就可以正常运行,而不关心该对象究竟是list还是其他数据类型
那么,我们该如何判断一个对象是可迭代对象呢?方法是通过collections模块的Iterable类型判断:
from collections import Iterable
d={'a':1,"b":2,"c":3}
print(isinstance(d,Iterable))
print(isinstance('ABC',Iterable))
print(isinstance(123,Iterable))
输出结果:
True
True
False
如果我们需要对list实现类似于java那样的下标循环该怎么办?Python内置的enumerate函数可以把一个list变成索引-元素对,这样就可以在for循环中同时迭代索引和元素本身:
for x, value in enumerate(['a','b','c']):
print(x,value)
输出为:
0 a
1 b
2 c
可见,在for循环中可以同时使用两个甚至是多个变量
列表生成式
可以用来创建list的生成式
例如我们需要生成list[1,2,3,4,5,6,7,8,9,10],可以使用list(range(1,11))
;要生成[1×1,2×2,….10×10],这个时候我们就需要用到循环
for x in range(1,11):
L.append(x*x)
使用循环会比较繁琐,我们使用列表生成式可以用一行语句生成上面的list:[x*x for x in range(1,11)]
;写生成表达式时,把需要生成的元素x*x 放在前面,后面接上for循环,就可将list创建出来,我们还可以在for循环后面加上if判断,这样我们就可以筛选出满足if条件的数据;
print([x*x for x in range(1,11) if x%2 ==0])
结果为[4, 16, 36, 64, 100]
另外还可以使用两层循环,可以生成全排列:
print([m+n for m in 'ABC' for n in 'DEF'])
#下面是输出
['AD', 'AE', 'AF', 'BD', 'BE', 'BF', 'CD', 'CE', 'CF']
可见,我们在列表生成式中也可以使用想循环中的多个变量
生成器
在Python中,有一种边循环边计算的机制,成为生成器:generator。列表元素可以按照某种算法推算出来,那我们就可以在循环的过程中不断推算出后续的元素,这样就不必创建完整的list,从而就能节省大量的空间。
创建generator的方法:
①将列表生成式中的[]
改为()
,这样就创建了一个generator
L=[x*x for x in range(1,11)]
print(L)
g=L=(x*x for x in range(1,11))
print(g)
print(next(g))
print(next(g))
输出:
[1, 4, 9, 16, 25, 36, 49, 64, 81, 100]
<generator object <genexpr> at 0x000002516B168200>
1
4
在上面输出g的时候,我们可以使用一个for循环进行迭代,同样可以获取其中的元素,主要,在使用next(g)这个函数的时候,当计算到最后一个元素,没有更多元素的时候,抛出StopIteration的错误
②在函数中使用yield
关键字
在这里是用的斐波拉契数列这个例子,斐波拉契数列也就是除了第一个和第二个数外,任意一个数都可以由前两个数相加得到
def fib(max):
n,a,b=0,0,1
while n<max:
print(b)
a,b=b,a+b
n=n+1
return 'done'
这个时候,我们将print(b)改为 yield b,fib函数就变成了generator,我们可以尝试输出fib函数的值,我们将得到以下结果:
<generator object fib at 0x000001B429C38200>
注意:generator跟函数的执行流程不一样,函数是顺序执行,遇到return语句或者最后一行函数语句就返回。而变成generator的函数,在每次调用next()的时候,遇到yield语句返回,再次执行时从上次返回的yield语句处继续执行
迭代器
到现在为止,我们已经知道,可以直接作用于for循环的数据类型有以下几种:一种是集合数据类型,如list、tuple、dict、set、str,另一类是generator,包括生成器和带yield的generator function;这些数据类型统称为可迭代对象:Iterable。在之前遇到过,我们可以使用isinstance()判断一个对象是否是Iterable对象:最终我们发现,list、dict、str虽然是Iterable,但不是Iterator,我们可以使用iter()这个函数将这些变为Iterator。
**解释:**Python的Iterator对象表示的是一个数据流,Iterator对象可以被next()函数调用并不断返回下一个数据,直到没有数据时抛出StopIteration错误。可以把这个数据流看做是一个有序序列,但我们却不能提前知道序列的长度,只能不断通过next()函数实现按需计算下一个数据,所以Iterator的计算是惰性的,只有在需要返回下一个数据时它才会计算。
Iterator甚至可以表示一个无限大的数据流,例如全体自然数。而使用list是永远不可能存储全体自然数的。