失眠网,内容丰富有趣,生活中的好帮手!
失眠网 > python生成矩阵为何[[0 for i in range(n)] for j in range(m)]而不能[[0]*n]*m

python生成矩阵为何[[0 for i in range(n)] for j in range(m)]而不能[[0]*n]*m

时间:2018-12-17 22:58:38

相关推荐

python生成矩阵为何[[0 for i in range(n)] for j in range(m)]而不能[[0]*n]*m

python生成矩阵,使用[[0]*n]*m,我们会发现,当改变其中某一个元素时,整列数据都会发生改变,而使用[[0 for i in range(n)] for j in range(m)]才可以生成正常的矩阵。

这是因为,list是可变元素,而int是不可变元素,对于list存储采用指针,引用型变量,改变矩阵其中某一个元素值,导致所有行的这个位置的元素都会改变。下面具体分析:

1、python列表的存储形式

Python列表和C语言数组不同,并不是存的实在的值,而是存放的只想其他实例的指针。所以也就能够理解 为什么python列表里里面什么东西都可以放进去而不需要考虑类型了~

2、 [0] * 2的存储形式

这里的 0 是同一个实例,可以通过以下代码发现这点~

(id表示查看实例的唯一标识符~)

3、 [[0]*2]*2的存储形式

下面两个箭头代表着下面的两行其实就是指向第一行两个指针,所以这里更改任意一行,都会对其他行产生影响,如图:

这里明明只更改了第三行的第三个元素,但是所有行的第三个元素都发生了变化,所以这也说明了指针这一特性,[[0]2]2所产生的其他行都只是简单的指向第一行,不是进行复制 **,所以更改任意一行,其他行都会产生变化!

4、 [[0 for i in range(3)] for j in range(3)]

虽然里面所有的0 都是一个实例,但是进行修改时,修改的是不同的列表,如图:

(这里的lst就是用上面的 [[0]*3]*3来产生的,而another是由列表解析式产生的),可以看出,lst每一行的id都是一样的,而another是不一样的,即代表着不同的行,修改其中一行并不会对另外的行产生影响。

也有小伙伴会问了,那列表解析式里面每个元素都是同一个,修改其中一个难道不会对其他有影响吗,这里我贴出一下代码,朋友们可以自行测试一下。

aa = [0 for i in range(3)]# 不可变类型for i in aa: print(id(i))aa = [[0] for i in range(3)] # 可变类型for i in aa: print(id(i))aa = ['1' for i in range(3)] # 不可变类型for i in aa: print(id(i))aa = [(1,2) for i in range(3)]# 不可变类型for i in aa: print(id(i))

不可变类型修改的时候是创建一个全新的实例,如果每个id都不一样的话,会非常耗费内存,而且一般不会对其他东西有影响,所以就创建相同的实例,但是可变类型不能这样,可变类型如果id相同,那么修改他们的元素会对其他实例产生影响,所以每个实例都应该是一个全新的实例

归根结底,还是我这里第一条所概述的,Python的列表存储方式是用的指针指向实例地址来存储的,列表里面放的就是指针的地址。

所以,君不见python里面没有指针,但是指针始终如影随形。😁

如果觉得《python生成矩阵为何[[0 for i in range(n)] for j in range(m)]而不能[[0]*n]*m》对你有帮助,请点赞、收藏,并留下你的观点哦!

本内容不代表本网观点和政治立场,如有侵犯你的权益请联系我们处理。
网友评论
网友评论仅供其表达个人看法,并不表明网站立场。