Python - 嵌套的 __repr__ 将换行符恢复为“\\n”
Posted
技术标签:
【中文标题】Python - 嵌套的 __repr__ 将换行符恢复为“\\\\n”【英文标题】:Python - nested __repr__ reverts newline to "\\n"Python - 嵌套的 __repr__ 将换行符恢复为“\\n” 【发布时间】:2016-04-05 02:24:55 【问题描述】:class MyClass:
def __init__(self):
self.list_ = []
def __repr__(self):
return '\n'.join(['this','should','all','be','on','separate','lines']) + str([str(list_val) for list_val in self.list_])
myClass = MyClass()
myClass.list_.append(MyClass())
myClass.list_[0].list_.append(MyClass())
print(myClass)
我希望这段代码能打印出来:
this
should
all
be
on
separate
lines[this
should
all
be
on
separate
lines[this
should
all
be
on
separate
lines]]
或类似的东西,但它会打印
this
should
all
be
on
separate
lines["this\nshould\nall\nbe\non\nseparate\nlines['this\\nshould\\nall\\nbe\\non\\nseparate\\nlines[]']"]
也就是说,当我尝试在同一类的另一个对象的__repr__
方法中将一个对象转换为字符串时,它会将换行符转换为\n
,如果我进一步嵌套它会导致\\n
,每次我嵌套它时,它都会在转义序列之前添加一个额外的反斜杠。
看了this question之后,好像__repr__
方法认为我其实想要\
和n
这两个字符,但是我不:我想要转义序列\n
。有没有办法覆盖它并强制它解释为换行符而不是两个单独的字符?
【问题讨论】:
【参考方案1】:问题在于字符串的repr
将特殊字符转换为转义序列。这意味着如果您在带有特殊字符的字符串上递归调用 repr
,反斜杠将会堆积:
>>> print("First line\nSecond line")
First line
Second line
>>> print(repr("First line\nSecond line"))
'First line\nSecond line'
>>> print(repr(repr("First line\nSecond line")))
"'First line\\nSecond line'"
您遇到这种情况是因为您的 __repr__
在列表中调用 str
,而列表的 str
在列表:
>>> print('First line\nSecond line')
First line
Second line
>>> print(['First line\nSecond line'])
['First line\nSecond line']
注意\n
出现在这里,就像在第一个示例中对字符串本身调用repr
所做的一样。这是因为列表在其内容上调用 repr
以显示自己。
所以通过str([...])
,您在列表的内容上调用repr
,这意味着您正在递归调用repr
您的嵌套对象,这意味着反斜杠堆积如您所见。
如果你想避免这种情况,你需要避免在嵌套对象上调用 repr。您可以通过使用join
手动制作一个字符串来做到这一点,类似于您已经做过的,而不是在列表上调用str
:
def __repr__(self):
innerRepr = '['+'\n'.join(str(list_val) for list_val in self.list_) + ']' if self.list_ else ''
return '\n'.join(['this','should','all','be','on','separate','lines']) + innerRepr
那么你的print(myClass)
会给出你想要的结果。
【讨论】:
哇,惊人的答案——难度级别 11。以上是关于Python - 嵌套的 __repr__ 将换行符恢复为“\\n”的主要内容,如果未能解决你的问题,请参考以下文章