UTF-8 with bom
UTF-8是一种常见的编码格式,一种是 含BOM,一种是 不含BOM
BOM 即byte order mark,带BOM的UTF-8文件的开头会有 U+FEFF 字符。
在 UTF-8 文件中放置 BOM 主要是 微软 的习惯,但是放在其他系统(linux、unix)上会出现问题。
注意:
不含BOM的UTF-8才是 标准形式 ,UTF-8不需要BOM
测试
使用windows系统的notepad工具新建 文本文件,内容为空,另存选择 UTF-8,如下图:
然后查看该文件属性,其长度为 3字节,而不是0字节,如下图:
说明使用notepad工具保存的UTF-8格式文件,是含有 BOM 的。
但这3个字节 不可显示,所以 看不见
注意:
必须是notepad工具,其他工具保存的utf-8,可能无bom
读取UTF-8 with bom文件
使用windows自带文本编辑器notepad工具新建文本文件,内容如下:
床前明月光
疑是地上霜
举头望明月
低头思故乡
保存为utf-8格式
注意:
使用notepad保存的utf-8,是有bom的
通过文本文件模式读取
代码如下
with open('c:/users/mym/desktop/1.txt','r',encoding='utf-8') as f:
c=f.read()
print(c)
空格就是无法正常显示的字符 U+FEFF
通过debug模式跟踪代码,可查看到该字符,如下图:
红框处就是 U+FEFF
去掉多余的bom
with open('c:/users/mym/desktop/1.txt','r',encoding='utf-8') as f:
c=f.read()
d=c[1:]#截取字符串,去掉开头的bom
print(d)
print(len(d))
长度为23,debug模式跟踪代码,发现换行符是\n,20个汉字加上3个\n,所以长度是23
注意:
windows平台的换行符是\r\n,占2个字符,在python中以文本文件模式读取,转换成\n了
注意:
上面的程序有bug,如果读取没有bom的utf-8文件,就会缺少第一个字符
支持读取UTF-8 without bom和with bom文件
完善上面的程序,使其可以读取utf-8 with bom和without bom的文件,代码如下
def readutf(file):
with open(file,'r',encoding='utf-8') as f:
data=f.read()
if data[0:1]=='\ufeff':
data=data[1:]
return data
content=readutf('c:/users/mym/desktop/6-1.txt')
print(content)
通过二进制模式读取
with open('c:/users/mym/desktop/1.txt','rb') as f:
c=f.read()
print(c)
通过debug模式跟踪代码,可查看到bom的3个字节,如下图:
去掉多余的bom
with open('c:/users/mym/desktop/1.txt','rb') as f:
b=f.read()
c=b[3:].decode('UTF-8')#将二进制解码为字符串
print(c)
print(len(c))
长度为26,debug模式跟踪代码,发现换行符是\r\n(windows平台的换行方式,占2个字符),20个汉字加上3个\r\n,所以长度是26
注意:
上面的程序有bug,如果读取没有bom的utf-8文件,就会缺少第一个字符
注意:
decode()方法参见链接:
http://www.malaoshi.top/show_1EF2Pg2sje3N.html
支持读取UTF-8 without bom和with bom文件
完善上面的程序,使其可以读取utf-8 with bom和without bom的文件,代码如下
def readutf(file):
with open(file,'rb') as f:
data=f.read()
if data[0:3]==b'\xef\xbb\xbf':
data=data[3:]
return data.decode('UTF-8')
content=readutf('c:/users/mym/desktop/6-1.txt')
print(content)
注意:
在判断b'\xef\xbb\xbf'时,可以使用codecs模块的BOM_UTF8属性,见下面代码:
import codecs
print(codecs.BOM_UTF8)
其结果就是:
b'\xef\xbb\xbf'
将上面的程序改动如下:
import codecs
f=open('c:/users/mym/desktop/1.txt','rb')
data=f.read()
if data[:3]==codecs.BOM_UTF8:
data=data[3:]
print(data.decode('utf-8'))
感谢下面链接
https://blog.csdn.net/legendaryhsl/article/details/78794121



