【问题标题】:Why ascii+ast.literal_eval conversion and deconversion return an object of different size?为什么 ascii+ast.literal_eval 转换和反转换返回不同大小的对象?
【发布时间】:2021-03-19 16:16:06
【问题描述】:

如果您使用ascii 将对象/列表转换为字符串,然后使用eval 转换回来,您将获得相同字节大小的相同表示。
为什么ast.literal_eval 回馈不同大小的对象?

a = [{"a": {"b": False}, True: 1}, 2, (3,6), ('g',),{"jfg"}]
b = ascii(a)
c = eval(b)
d = ast.literal_eval(b)
print(f"a: {sys.getsizeof(a)}\t{type(a)}\t{a}\nb: {sys.getsizeof(b)}\t{type(b)}\t{b}\nc: {sys.getsizeof(c)}\t{type(c)}\t{c}\nd: {sys.getsizeof(d)}\t{type(d)}\t{d}")
a: 96   <class 'list'>  [{'a': {'b': False}, True: 1}, 2, (3, 6), ('g',), {'jfg'}]
b: 107  <class 'str'>   [{'a': {'b': False}, True: 1}, 2, (3, 6), ('g',), {'jfg'}]
c: 96   <class 'list'>  [{'a': {'b': False}, True: 1}, 2, (3, 6), ('g',), {'jfg'}]
d: 120  <class 'list'>  [{'a': {'b': False}, True: 1}, 2, (3, 6), ('g',), {'jfg'}]

将对象转换为字符串并返回的更好/更安全/更快/更轻的方法是什么?

【问题讨论】:

  • 列表的大小可能取决于用于创建它的特定函数,因为它会随着元素的添加而动态增长。
  • 只需比较:sys.getsizeof(eval('[13]'))sys.getsizeof(ast.literal_eval('[13]'))
  • @Barmar 你的意思是literal_eval 正在向列表中添加元素而eval 没有?
  • 也许吧。您必须查看源代码才能准确了解它们的工作原理。
  • literal_eval() 可能是用 Python 编写的,因此它会逐步构建列表,而 eval() 是一个内置函数,可以利用内部函数来创建具有指定大小的列表。跨度>

标签: python type-conversion ascii eval


【解决方案1】:

在事物的宏大主题中,与ast.literal_eval无关。

Python 列表是动态的。它们可以增长和缩小。

您使用文字列表对象(即a)创建列表,运行时确切地知道它需要分配多少内存。

当您以任何其他方法创建列表时,很难预测列表最终会有多大,因此runtime allocates memory using a specific algorithm,以确保不浪费内存,但另一方面,尝试不要太频繁地重新分配内存,因为那样效率不高。

您可以通过简化示例来重现相同的行为。例如,创建一个空列表然后扩展它:

import sys

literal_list = [{"a": {"b": False}, True: 1}, 2, (3,6), ('g',),{"jfg"}]
print(f"a: {sys.getsizeof(literal_list)}\t{type(literal_list)}\t{literal_list}")
li = []
li.extend([{"a": {"b": False}, True: 1}, 2, (3,6), ('g',),{"jfg"}])
print(f"li: {sys.getsizeof(li)}\t{type(li)}\t{li}")

输出

a: 48   <class 'list'>  [{'a': {'b': False}, True: 1}, 2, (3, 6), ('g',), {'jfg'}]
li: 60  <class 'list'>  [{'a': {'b': False}, True: 1}, 2, (3, 6), ('g',), {'jfg'}]

【讨论】:

  • 为什么你说你的例子简化了我的例子?我不是故意修改bliteral_eval 是否会以某种方式修改列表,而 eval 不会?
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2021-01-20
  • 2019-04-14
  • 1970-01-01
  • 1970-01-01
  • 2011-04-10
  • 1970-01-01
  • 2019-02-02
相关资源
最近更新 更多