python元组的内部结构 [英] Internals for python tuples

查看:40
本文介绍了python元组的内部结构的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

<预><代码>>>>a=1>>>b=1>>>身份证(一)140472563599848>>>身份证(二)140472563599848>>>x=()>>>y=()>>>编号(x)4298207312>>>编号(y)4298207312>>>x1=(1)>>>x2=(1)>>>身份证(x1)140472563599848>>>身份证(x2)140472563599848

到目前为止,我一直认为只有一个不可变对象的副本,并且所有变量都将共享(指向).

但是当我尝试时,下面的步骤我明白我错了.

<预><代码>>>>x1=(1,5)>>>y1=(1,5)>>>身份证(x1)4299267248>>>编号(y1)4299267320

谁能解释一下内部原理?

解决方案

>>>x1=(1)>>>x2=(1)

其实是一样的

<预><代码>>>>x1=1>>>x2=1

在 Python 中,较小的数字在内部缓存.所以它们不会在内存中多次创建.这就是为什么 x1x2id 到目前为止是相同的.

一个单元素元组的末尾应该有一个逗号,就像这样

<预><代码>>>>x1=(1,)>>>x2=(1,)

执行此操作时,将构造两个新元组,其中只有一个元素.尽管元组中的元素相同,但它们都是不同的元组.这就是为什么它们都有不同的 ids.

让我们以你的最后一个例子反汇编代码.

compiled_code = compile("x1 = (1, 5); y1 = (1, 5)", "string", "exec")

现在,

导入文件dis.dis(compiled_code)

会产生这样的东西

 1 0 LOAD_CONST 3 ((1, 5))3 STORE_NAME 0 (x1)6 LOAD_CONST 4 ((1, 5))9 STORE_NAME 1 (y1)12 LOAD_CONST 2(无)15 RETURN_VALUE

它加载一个常量值,由索引 3 引用,即 (1, 5),然后将其存储在 x1 中.以同样的方式,它在索引 4 处加载另一个常量值并将其存储在 y1 中.如果我们查看代码对象中的常量列表,

print(compiled_code.co_consts)

会给

(1, 5, None, (1, 5), (1, 5))

34 位置的元素是我们在实际代码中创建的元组.因此,Python 不会为每个不可变对象只创建一个实例,总是.它是一个实现细节,我们无论如何都不必担心.

注意:如果你只想拥有一个不可变对象的实例,你可以像这样手动操作

x1 = (1, 5)x2 = x1

现在,x2x1 将引用同一个元组对象.

>>> a=1
>>> b=1
>>> id(a)
140472563599848
>>> id(b)
140472563599848
>>> x=()
>>> y=()
>>> id(x)
4298207312
>>> id(y)
4298207312
>>> x1=(1)
>>> x2=(1)
>>> id(x1)
140472563599848
>>> id(x2)
140472563599848

until this point I was thinking there will be only one copy of immutable object and that will be shared(pointed) by all the variables.

But when I tried, the below steps I understood that I was wrong.

>>> x1=(1,5)
>>> y1=(1,5)
>>> id(x1)
4299267248
>>> id(y1)
4299267320

can anyone please explain me the internals?

解决方案

>>> x1=(1)
>>> x2=(1)

is actually the same as

>>> x1=1
>>> x2=1

In Python, smaller numbers are internally cached. So they will not be created in the memory multiple times. That is why ids of x1 and x2 are the same till this point.

An one element tuple should have a comma at the end, like this

>>> x1=(1,)
>>> x2=(1,)

When you do this, there are two new tuples to be constructed with only one element in it. Even though the elements inside the tuples are the same, they both are different tuples. That is why they both have different ids.

Lets take your last example and disassemble the code.

compiled_code = compile("x1 = (1, 5); y1 = (1, 5)", "string", "exec")

Now,

import dis
dis.dis(compiled_code)

would produce something like this

  1           0 LOAD_CONST               3 ((1, 5))
              3 STORE_NAME               0 (x1)
              6 LOAD_CONST               4 ((1, 5))
              9 STORE_NAME               1 (y1)
             12 LOAD_CONST               2 (None)
             15 RETURN_VALUE

It loads a constant value, referred by the index 3, which is (1, 5) and then stores it in x1. The same way, it loads another constant value, at index 4 and stores it in y1. If we look at the list of constants in the code object,

print(compiled_code.co_consts)

will give

(1, 5, None, (1, 5), (1, 5))

The elements at positions 3 and 4 are the tuples which we created in the actual code. So, Python doesn't create only one instance for every immutable object, always. Its an implementation detail which we don't have to worry much about anyway.

Note: If you want to have only one instance of an immutable object, you can manually do it like this

x1 = (1, 5)
x2 = x1

Now, both x2 and x1 will refer the same tuple object.

这篇关于python元组的内部结构的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆