重写Python打印语句的换行行为
我有一堆老旧的代码,用来处理原始邮件的编码,这些代码里有很多打印语句,比如:
print >>f, "Content-Type: text/plain"
这对于邮件来说没问题,但我们现在也想用这段代码来输出HTTP请求。问题是,Python的打印语句输出的是'\n'
,而HTTP需要的是'\r\n'
。
看起来Python(至少是2.6.4版本)在打印语句后会生成一个额外的PRINT_NEWLINE
字节码,具体实现是:
ceval.c:1582: err = PyFile_WriteString("\n", w);
所以,似乎没有简单的方法可以改变打印的默认换行行为。我考虑了以下几种解决方案:
.replace('\n', '\r\n')
来替换。这会影响使用多部分编码的HTTP消息。.write
方法。def write(self, data):
if data == '\n':
data = '\r\n'
return self._file.write(data)
print >>f, text
转换成f.write(text + line_end)
,其中line_end
可以是'\n'
或'\r\n'
。我认为第三个选项是最合适的。听听你们的Python解决方案会是什么样的,应该很有趣。
6 个回答
4
在python2.x中,我觉得你可以这样做:
print >>f "some msg\r\n",
这样可以去掉最后的换行符。
在python3.x中,这个过程简单多了:
print("some msg", end = "\r\n", file = f)
8
(不确定这是否适合你打算使用的包装器,但以防万一……)
在Python 2.6(以及许多之前的版本)中,你可以通过在print语句的末尾加一个逗号来抑制换行,比如这样:
data = 'some msg\r\n'
print data, # note the comma
不过,使用这种方法的缺点是,Python 3中的print语法和行为发生了变化。
10
你现在可以通过定义一个新的输出函数来解决你的问题,这样就能永远解决了。如果是用打印函数的话,这会简单很多。
我建议你写一个新的输出函数,尽量模仿现代打印函数的样子(因为重用一个好的接口是很有帮助的),比如:
def output(*items, end="\n", file=sys.stdout):
pass
一旦你把所有需要的打印都替换成这个新的函数,你就不再有这个问题了——你可以随时改变这个函数的行为!这就是为什么在Python 3中把打印做成一个函数的一个重要原因——因为在Python 2.x中,所有项目都会经历一个阶段,所有的print
语句都变得不灵活,而没有简单的解决办法。