我想用空字符(“\ x00”)填充字符串。我知道有很多方法可以做到这一点,所以请不要用其他方式回答。我想知道的是:为什么Python的string.format()
函数不允许使用空值填充?
测试用例:
>>> "{0:\x01<10}".format("bbb")
'bbb\x01\x01\x01\x01\x01\x01\x01'
这表明十六进制转义字符一般都有用。
>>> "{0:\x00<10}".format("bbb")
'bbb '
但是“\ x00”变成了一个空格(“\ x20”)。
>>> "{0:{1}<10}".format("bbb","\x00")
'bbb '
>>> "{0:{1}<10}".format("bbb",chr(0))
'bbb '
甚至尝试了其他一些方法。
>>> "bbb" + "\x00" * 7
'bbb\x00\x00\x00\x00\x00\x00\x00'
这样可行,但不使用string.format
>>> spaces = "{0: <10}".format("bbb")
>>> nulls = "{0:\x00<10}".format("bbb")
>>> spaces == nulls
True
Python显然用空格(chr(0x20)
)代替空格(chr(0x00)
)。
答案 0 :(得分:4)
深入研究Python 2.7的源代码,我发现问题出在本节的./Objects/stringlib/formatter.h
,第718-722行(版本2.7.3)中:
/* Write into that space. First the padding. */
p = fill_padding(STRINGLIB_STR(result), len,
format->fill_char=='\0'?' ':format->fill_char,
lpad, rpad);
问题是当没有指定填充字符时,零/空字符('\0'
)被用作默认值。这是为了启用此行为:
>>> "{0:<10}".format("foo")
'foo '
有可能在format->fill_char = ' ';
parse_internal_render_format_spec()
处将./Objects/stringlib/formatter.h:186
设置为默认值,但稍后会检查'\0'
的向后兼容性。无论如何,我的好奇心得到了满足。如果它有更多的历史或更好的解释原因,我会接受别人的答案。
答案 1 :(得分:2)
原始问题的答案是它是python中的一个错误。
它被记录为被允许,但不是。它是在2014年修复的。对于python 2,修复程序首先出现在2.7.7或2.7.8(我不确定如何分辨哪个)
原始跟踪issue。
答案 2 :(得分:0)
因为Python2.7中的string.format
方法是Python3 string.format
的后端口。 Python2.7 unicode是Python 3字符串,其中Python2.7字符串是Python3字节。字符串是在Python3中表达二进制数据的错误类型。您将使用没有格式方法的字节。所以你真的应该问为什么2.7中的format
方法完全应该只用在unicode类型上,因为这就是Python3中的字符串。
我猜这个答案就是把它放在那里太方便了。
作为相关问题,为什么还没有format
on bytes