〇引言
对上篇博客知识的补充,也是个人笔记。现在离开手机简直不能活了,所以把笔记记录在博客上挺方便的。当然这个是纯笔记,没啥观赏性,还请见谅。
x=[[1,2,3],[4,5,6],[7,8,9]]
for i in x: #两个for语句
for each in i:
print(each)
1
2 #不算美观
3
4
5
6
7
8
9
for i in x:
for each in i:
print(each,end=' ') #end=' ' 以空格结尾
1 2 3 4 5 6 7 8 9
二维列表的下标索引
二维列表顾名思义,有行有列。在对python二维列表的直观认识应该是
x=[[1,2,3], #这样的
[4,5,6],
[7,8,9]]
即在x[ ]此处为行(每个小列表),x[][ ]此处为行里的哪一列(每个小列表里再拆分)
注意:python对于不同数据类型的储存机制。python对于不同对象的储存机制不一样。如下
b=[[0]*3]*3
a=[0,0,0]
for i in range(3):
a[i]=[0]*3
a
[[0, 0, 0], [0, 0, 0], [0, 0, 0]]
b
[[0, 0, 0], [0, 0, 0], [0, 0, 0]]
a is b
False
tips:同一性运算符 is 用于检验两个变量,是否指向同一个对象的运算符
由此可以看出a不等于b,来看一下他们的储存方式。
a指向三不同的[0,0,0],各自独立,而b是对同一个[0,0,0]的三个引用。就是说会出现下面的这种情况
#仍是上面的a,b
a[0][1]=3
b[0][1]=3
a
[[0, 3, 0], [0, 0, 0], [0, 0, 0]]
b
[[0, 3, 0], [0, 3, 0], [0, 3, 0]]
拷贝
提到引用就不得不说拷贝
浅拷贝:在不调用copy模块的情况下进行的copy
x=[1,2,3]
y=x
x[0]=4
x
[4, 2, 3]
y
[4, 2, 3] #注意,将x赋值给y时,改变x里的一个数据,y也会跟着改变
这就应证了我在第一篇博里写到"变量不是一个盒子。"
那么就有引用这一说法
引用:当赋值运算发生时,python不是将数据放到变量里,而是将一个变量的引用传递给另一个变量(将一个变量赋值给一个变量)
如果需要两个独立的列表要用copy函数(此处的copy为浅拷贝)
x=[1,2,3]
y=x.copy()
x[1]=9
y
[1, 2, 3]
x
[1, 9, 3]
我们也可以用切片的方法来实现
x=[4,5,6]
y=x[:]
x[0]=1
y
[4, 5, 6]
x
[1, 5, 6]
这是浅拷贝(只拷贝其表面),仅对一维列表有效。
#示例
x=[[1,2,3], #创建二维列表
[4,5,6],
[7,8,9]]
y=x.copy()
y
[[1, 2, 3], [4, 5, 6], [7, 8, 9]]
x[0][1]=9
y
[[1, 9, 3], [4, 5, 6], [7, 8, 9]] #x变,y也变
x
[[1, 9, 3], [4, 5, 6], [7, 8, 9]]
不论是y=x.copy(),y=x[:] 都是浅拷贝,只拷贝外层,内部是引用。
固我们需要调用copy模块(但注意y=copy.copy(x)这个是浅拷贝)
要真正调用深拷贝要用copy模块里的deepcopy函数
x=[[1,2,3], #二维列表
[4,5,6],
[7,8,9]]
import copy
y=copy.deepcopy(x)
x[0][1]=100
x
[[1, 100, 3], [4, 5, 6], [7, 8, 9]]
y
[[1, 2, 3], [4, 5, 6], [7, 8, 9]]
列表推导式
语法:[expression for target in iterable]
#实例
x=[i for i in range(10)]
x
[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]
这个语句的执行顺序是
执行在for语句中的range(10),把数据存放在for语句后的i,后放入列表表达式的i中。
也就是说,他的执行顺序是从后往前的。并且在列表表达式中再执行一次,及可在其中再执行相关语句
x=[i+1 for i in range(10)]
x
[1, 2, 3, 4, 5, 6, 7, 8, 9, 10]
#我们也可以用老方法现实
x=[]
for i in range(10):
x.append(i+1)
#由此可以看出列表推导式执行的便捷性
其他用法
y=[c*2 for c in 'love'] #在字符串上应用
y
['ll', 'oo', 'vv', 'ee']
#用ord()将字符转化为Unicode编码
code=[ord(c) for c in 'love']
code
[108, 111, 118, 101]
用列表推导式将矩阵第二列提取
x=[[1,2,3], #直观看一下二维列表
[4,5,6],
[7,8,9]]
#用英文名命名col=column列 row行
col2=[row[1] for row in x]
col2
[2, 5, 8]
内核就是把x二维列表的每一行的第二个数抽取组成新的列表
diag = [x[i][i] for i in range(len(x))] #提取斜对角线
diag
[1, 5, 9]
for i in range(len(x)) 首先len()获取列表x的长度,然后fanhuix[i][i],及[0][0],[1][1],[2][2]
diag = [x[-i][-i] for i in range(len(x))]
diag
[1, 9, 5]
#下标为负
diag = [x[i][2-i] for i in range(len(x))]
diag
[3, 5, 7]
#另一个对角线
用列表推导式建立矩阵
s=[[0]*3 for i in range(3)]
s
[[0, 0, 0], [0, 0, 0], [0, 0, 0]]
s[0][1]=100
s
[[0, 100, 0], [0, 0, 0], [0, 0, 0]] #注意这里三个小列表相互独立
可以在列表推导式加上条件语句
[expression for target in iterable if condition]
执行顺序是先for语句,然后if语句,最后for前的语句。例如
x=[i for i in range(10) if i%2==0]
x
[0, 2, 4, 6, 8]
#可以起到筛选的作用
word=['fan','coco','frank','female','apple','pear','fall']
f_word=[w for w in word if w[0]=='f']
f_word
['fan', 'frank', 'female', 'fall']
嵌套列表
#语法如下
[expression for target in iterable1
for target in iterable2
......
for target in iterableN]
可以拆分列表(注意顺序)
matrix=[[1,2,3],
[4,5,6],
[7,8,9]]
flatten=[col for row in matrix for col in row]
flatten
[1, 2, 3, 4, 5, 6, 7, 8, 9]
用老方法写
flatten=[]
for row in matrix:
for col in row:
flatten.append(col)
应用在字符串上
s=[x+y for x in 'love' for y in 'you']
s
['ly', 'lo', 'lu', 'oy', 'oo', 'ou', 'vy', 'vo', 'vu', 'ey', 'eo', 'eu']
for x in 'love':
for y in 'you':
s.append(x+y)
#这才是完整的语法
#语法如下
[expression for target in iterable1 if condition1
for target in iterable2 if condition2
......
for target in iterableN if conditionN]
#示例代码
s=[[x,y] for x in range(10) if x%2==0 for y in range(10) if y%3==0]
s
[[0, 0], [0, 3], [0, 6], [0, 9], [2, 0], [2, 3], [2, 6], [2, 9], [4, 0], [4, 3], [4, 6], [4, 9], [6, 0], [6, 3], [6, 6], [6, 9], [8, 0], [8, 3], [8, 6], [8, 9]]
#老方法
s=[]
for x in range(10):
if x%2==0:
for y in range(10):
if y%3==0:
s.append([x,y])
但这些花哨高级,但难以理解,我们编程应该遵守KISS原则,及Keep It Simple and Stupid
感谢阅读