【问题标题】:When python creates new objects in memory当python在内存中创建新对象时
【发布时间】:2017-08-18 19:17:31
【问题描述】:

在以下示例中,Python 在内存中为命名空间中的所有三个名称 x、y 和 z 使用相同的整数对象

def main():
    x = 0
    y = 0
    z = 0
    print(x,y,z)
    print(x is y is z)
    y = 2
    print(x,y,z)
    print(x is y)
    print(z is y)
    print(x is z)

if __name__ == "__main__":main()

输出:

0 0 0
True
0 2 0
False
False
True

为什么 Python 在这里不使用相同的元组对象(是的,这是语言设计者的选择,但为什么),一个更好的问题是 python 何时在内存中创建新对象

def main():
    a = 1, 2, 3
    b = (1, 2, 3)
    c = 1, 2, 3

    print(type(a) == type(b))
    print(a == b)
    print(a is b)
    print(a == c)
    print(a is c)

if __name__ == "__main__":main()

输出:

True
True
False
True
False

【问题讨论】:

  • 能否请您不要在您的问题中转储代码图片?总是有一个很好的选择,就是粘贴它。
  • 当 Python 创建一个新对象时,是依赖于实现的。在实践中,字符串文字被重用,传递给intern()的字符串被重用,小整数被重用,空元组被重用。在重用所有不可变对象和跟踪哪些不可变对象可重用之间需要权衡取舍。
  • @cᴏʟᴅsᴘᴇᴇᴅ:提问者知道is==之间的区别。问题是为什么元组是不​​同的对象,而不是为什么 is== 报告不同的东西。
  • @PM2Ring 谢谢我从现在开始做
  • 不要从现在开始,如果你edit现在你的问题对未来的访问者会更有用。

标签: python variable-assignment python-internals


【解决方案1】:

对于表示可变对象的文字,对文字的每次求值都必须生成一个新对象。

对于表示不可变对象的文字,是否创建新对象归结为任意实现细节。它本可以选择使用相同的元组。它可以在未来的版本中使用相同的元组,或者在不同的 Python 实现中使用。如果您重复调用main,您的示例实际上确实重用了元组,但abc 的元组不同。你不应该依赖它是一种或另一种方式。

如果您想查看此案例的特定实现细节,CPython bytecode compiler 通常将等效常量合并到一个代码对象中(该机制涉及一个 dict,需要一些额外的工作来保留 1.0 和 @987654328 之类的东西@ from merging),但预计算 3 个元组的 peephole optimization pass 发生在没有重复数据删除机制的后处理阶段。

【讨论】:

  • 谢谢,我需要事物背后的逻辑,这使我成为更好的编码器,实际上我也是这么想的,我希望 Python 重用内存中的元组,如果没有其他答案,我会接受这个答案跨度>
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2014-02-26
  • 1970-01-01
  • 2023-03-18
  • 1970-01-01
  • 2014-02-21
  • 2012-01-08
  • 2013-06-23
相关资源
最近更新 更多