在Python for Windows Notepad中创建UTF-16换行符

I_R*_*vic 1 python windows unicode notepad utf-16

在Python 2.7中运行Ubuntu这段代码:

f = open("testfile.txt", "w")
f.write("Line one".encode("utf-16"))
f.write(u"\r\n".encode("utf-16"))
f.write("Line two".encode("utf-16"))
Run Code Online (Sandbox Code Playgroud)

在Gedit中读取时,在两行文本之间生成所需的换行符:

Line one?
?Line two
Run Code Online (Sandbox Code Playgroud)

但是,在Windows 7中执行并在记事本中读取的相同代码会在"第一行"之后生成难以理解的字符,但记事本不会识别换行符.如何在Windows中为UTF-16编写正确的换行符以匹配我在Ubuntu中获得的输出?

我正在为只能读取Unicode UTF-16的Windows应用程序编写输出.我花了好几个小时尝试不同的提示,但似乎没有任何东西适用于记事本.值得一提的是,我可以在记事本中成功将文本文件转换为UTF-16,但我宁愿让脚本首先正确保存编码.

aba*_*ert 8

问题是您在文本模式下打开文件,但尝试将其用作二进制文件.

这个:

u"\r\n".encode("utf-16")
Run Code Online (Sandbox Code Playgroud)

......编码为'\r\0\n\0'.

然后这个:

f.write('\r\0\n\0')
Run Code Online (Sandbox Code Playgroud)

...将Unix换行符转换为Windows换行符'\r\0\r\n\0'.

当然,这会破坏您的UTF-16编码.除了两个\r\n字节将解码为有效但未分配的代码点U + 0A0D的事实,这是一个奇数个字节,这意味着你有一个剩余的\0.因此,而不是L\0成为下一个字符,这是\0L,又名?,等等.

最重要的是,您可能正在为每个编码字符串编写新的UTF-16 BOM.大多数Windows应用程序实际上都会透明地处理它并忽略它们,所以你实际上所做的只是浪费两个字节/行,但它实际上并不正确.


第一个问题的快速解决方法是以二进制模式打开文件:

f = open("testfile.txt", "wb")
Run Code Online (Sandbox Code Playgroud)

这不能解决多BOM问题,但它解决了破坏的\n问题.如果要修复BOM问题,可以使用有状态编码,也可以在第一次写入时明确指定'utf-16-le'(或'utf-16-be')所有写入.


但对于这两个问题,简单的解决方法是使用模块(或者,对于较旧的Python 2.x,模块)来为您完成所有艰苦的工作:iocodecs

f = io.open("testfile.txt", "w", encoding="utf-8")
f.write("Line one")
f.write(u"\r\n")
f.write("Line two")
Run Code Online (Sandbox Code Playgroud)