str(list)如何工作?

>>> x = ['abc', 'def', 'ghi']

>>> str(x)

"['abc', 'def', 'ghi']"

要从中获取原始列表,str(list)我必须:

>>> from ast import literal_eval

>>> x = ['abc', 'def', 'ghi']

>>> str(x)

"['abc', 'def', 'ghi']"

>>> list(str(x))

['[', "'", 'a', 'b', 'c', "'", ',', ' ', "'", 'd', 'e', 'f', "'", ',', ' ', "'", 'g', 'h', 'i', "'", ']']

>>> literal_eval(str(x))

['abc', 'def', 'ghi']

或者我可以使用:

>>> eval(str(x))

['abc', 'def', 'ghi']

例如

>>> x = 'abc'

>>> list(x)

['a', 'b', 'c']

>>> str(list(x))

"['a', 'b', 'c']"

>>> list(str(list(x)))

['[', "'", 'a', "'", ',', ' ', "'", 'b', "'", ',', ' ', "'", 'c', "'", ']']

>>> str(list(str(list(x))))

'[\'[\', "\'", \'a\', "\'", \',\', \' \', "\'", \'b\', "\'", \',\', \' \', "\'", \'c\', "\'", \']\']'

>>> list(str(list(str(list(x)))))

['[', "'", '[', "'", ',', ' ', '"', "'", '"', ',', ' ', "'", 'a', "'", ',', ' ', '"', "'", '"', ',', ' ', "'", ',', "'", ',', ' ', "'", ' ', "'", ',', ' ', '"', "'", '"', ',', ' ', "'", 'b', "'", ',', ' ', '"', "'", '"', ',', ' ', "'", ',', "'", ',', ' ', "'", ' ', "'", ',', ' ', '"', "'", '"', ',', ' ', "'", 'c', "'", ',', ' ', '"', "'", '"', ',', ' ', "'", ']', "'", ']']

>>> str(list(str(list(str(list(x))))))

'[\'[\', "\'", \'[\', "\'", \',\', \' \', \'"\', "\'", \'"\', \',\', \' \', "\'", \'a\', "\'", \',\', \' \', \'"\', "\'", \'"\', \',\', \' \', "\'", \',\', "\'", \',\', \' \', "\'", \' \', "\'", \',\', \' \', \'"\', "\'", \'"\', \',\', \' \', "\'", \'b\', "\'", \',\', \' \', \'"\', "\'", \'"\', \',\', \' \', "\'", \',\', "\'", \',\', \' \', "\'", \' \', "\'", \',\', \' \', \'"\', "\'", \'"\', \',\', \' \', "\'", \'c\', "\'", \',\', \' \', \'"\', "\'", \'"\', \',\', \' \', "\'", \']\', "\'", \']\']'

>>> list(str(list(str(list(str(list(x)))))))

['[', "'", '[', "'", ',', ' ', '"', "'", '"', ',', ' ', "'", '[', "'", ',', ' ', '"', "'", '"', ',', ' ', "'", ',', "'", ',', ' ', "'", ' ', "'", ',', ' ', "'", '"', "'", ',', ' ', '"', "'", '"', ',', ' ', "'", '"', "'", ',', ' ', "'", ',', "'", ',', ' ', "'", ' ', "'", ',', ' ', '"', "'", '"', ',', ' ', "'", 'a', "'", ',', ' ', '"', "'", '"', ',', ' ', "'", ',', "'", ',', ' ', "'", ' ', "'", ',', ' ', "'", '"', "'", ',', ' ', '"', "'", '"', ',', ' ', "'", '"', "'", ',', ' ', "'", ',', "'", ',', ' ', "'", ' ', "'", ',', ' ', '"', "'", '"', ',', ' ', "'", ',', "'", ',', ' ', '"', "'", '"', ',', ' ', "'", ',', "'", ',', ' ', "'", ' ', "'", ',', ' ', '"', "'", '"', ',', ' ', "'", ' ', "'", ',', ' ', '"', "'", '"', ',', ' ', "'", ',', "'", ',', ' ', "'", ' ', "'", ',', ' ', "'", '"', "'", ',', ' ', '"', "'", '"', ',', ' ', "'", '"', "'", ',', ' ', "'", ',', "'", ',', ' ', "'", ' ', "'", ',', ' ', '"', "'", '"', ',', ' ', "'", 'b', "'", ',', ' ', '"', "'", '"', ',', ' ', "'", ',', "'", ',', ' ', "'", ' ', "'", ',', ' ', "'", '"', "'", ',', ' ', '"', "'", '"', ',', ' ', "'", '"', "'", ',', ' ', "'", ',', "'", ',', ' ', "'", ' ', "'", ',', ' ', '"', "'", '"', ',', ' ', "'", ',', "'", ',', ' ', '"', "'", '"', ',', ' ', "'", ',', "'", ',', ' ', "'", ' ', "'", ',', ' ', '"', "'", '"', ',', ' ', "'", ' ', "'", ',', ' ', '"', "'", '"', ',', ' ', "'", ',', "'", ',', ' ', "'", ' ', "'", ',', ' ', "'", '"', "'", ',', ' ', '"', "'", '"', ',', ' ', "'", '"', "'", ',', ' ', "'", ',', "'", ',', ' ', "'", ' ', "'", ',', ' ', '"', "'", '"', ',', ' ', "'", 'c', "'", ',', ' ', '"', "'", '"', ',', ' ', "'", ',', "'", ',', ' ', "'", ' ', "'", ',', ' ', "'", '"', "'", ',', ' ', '"', "'", '"', ',', ' ', "'", '"', "'", ',', ' ', "'", ',', "'", ',', ' ', "'", ' ', "'", ',', ' ', '"', "'", '"', ',', ' ', "'", ']', "'", ',', ' ', '"', "'", '"', ',', ' ', "'", ']', "'", ']']

回答:

好吧,您总共有4个问题,让我们一一解答。

什么是str()__str__()

str()调用是返回一个 可打印的

仅为对象的形式!来自文档

str(object)并不总是尝试返回可接受的字符串eval(); 它的目标是返回可打印的字符串。

__str__()每当您调用str()对象时,都会调用类中的函数。再次从文档

object.__str__(self)

str()内置函数和print语句调用以计算对象的“非正式”字符串表示形式。

list可调用的是什么?

list()调用是创建一个迭代器作为参数传递的列表。再次从文档

返回list其项目与iterable的项目相同且顺序相同的

因此,str(list)为您提供了可打印的形式,list(str(list))并将遍历字符串。这list(str(list))将为您提供传递的参数的可打印形式的各个字符的列表。

嵌套调用之间的一小步漫游,

给定列表,l = ['a','b'] (为您举一个比您的问题小的示例的道歉)。

调用时str(l),它将返回列表的可打印形式l,即"['a','b']"

现在您可以清楚地看到这"['a','b']"是一个字符串,并且确实是 可迭代的

。现在,当您调用list此方法时,即list("['a','b']")会得到一个像这样的怪异列表['[', "'", 'a', "'", ',',

"'", 'b', "'", ']']为什么会这样? 发生这种情况是因为字符串会遍历其字符,您可以使用虚拟字符串进行测试,

>>> 'dummy'

'dummy'

>>> list('dummy')

['d', 'u', 'm', 'm', 'y']

因此,当您list在字符串上调用时,会得到一个字符列表。请注意,再次在此处调用str()list('dummy'),将不会取回原始字符串'dummy',因此必须再次使用join!因此,调用相同的功能

使您回到原来的对象!

回答:

每当您调用str()列表对象时,遵循的步骤是

  1. 调用repr()每个列表元素。
  2. [在列表的前面添加一个花式],在列表的末尾添加另一个。
  3. 用逗号将它们全部加入。

github上cpython中的列表对象的源代码中可以看到。在hg.python中仔细阅读cpython的源代码,您会看到以下三个注释。(感谢Ashwini提供该特定代码上的链接)

/* Do repr() on each element.  Note that this may mutate the list,

so must refetch the list size on each iteration. */ line (382)

/* Add "[]" decorations to the first and last items. */ line (398)

/* Paste them all together with ", " between. */ line (418)

这些与我上面提到的要点相对应。

现在是什么repr()

repr()打印所有对象的字符串表示形式。再次从文档

返回一个包含对象可打印表示形式的字符串。

还要注意这句话!

对于许多类型,此函数会尝试返回一个字符串,该字符串将在传递给时产生一个具有相同值的对象eval(),否则表示形式是一个用尖括号括起来的字符串,其中包含对象类型的名称以及其他信息通常包括对象的名称和地址。

现在你在这里的第二个问题,

在内部,str(list)实际上创建repr()列表对象的表示形式。因此,在调用列表后要返回str列表,您实际上需要执行eval此操作而不是list调用。

解决方法

但是我们都知道那eval

邪恶的

,那么解决方法是什么?

回答:

literal_eval

第一个解决方法是使用ast.literal_eval。这使我们想到了第三个问题,

ast.literal_eval()eval()功能不同是安全的。文档本身提到它很安全-

安全地 评估表达式节点或包含Python文字或容器显示的字符串

回答:

另一个解决方法可以使用

str.split()

>>> x = ['abc', 'def', 'ghi']

>>> a = str(x)

>>> a[2:-2].split("', '")

['abc', 'def', 'ghi']

这只是对字符串列表执行此操作的一种简单方法。对于整数列表,您将需要map

>>> x = [1,2,3]

>>> a =str(x)

>>> list(map(int,a[1:-1].split(', '))) # No need for list call in Py2

[1, 2, 3]

因此,与literal_eval这些不同的是,只要您知道列表的元素,这些都是简单的技巧。如果它们本质上是异类的,[1, "a",

True]那么您将不得不遍历拆分列表并发现元素类型,然后将其转换并将转换后的元素附加到最终列表中。

失败的另一个地方是字符串本身包含引号字符。正如nneonneo)在评论中提到的

str.split解决方案非常脆弱,如果输入包含例如包含",

",元组或其他列表的字符串,则该解决方案会中断。…最好使用ast.literal_eval该解决方案,因为它将处理语法的所有细微问题。

对于您的最后一个问题,

并不是的。每次您创建alist的a

str,然后再次获取其可打印版本时,输出将越来越长。该限制仅是您的物理计算机的限制。(将字符串长度乘以5后很快就会达到)。

以上是 str(list)如何工作? 的全部内容, 来源链接: utcz.com/qa/420209.html

回到顶部