我的Python只能用记事本打开保存的文本文件,为什么?

0 投票
1 回答
1419 浏览
提问于 2025-04-18 13:57

我在用Python 3.4.1和Windows 7。我想读取一个从软件导出的txt文件,但似乎Python无法读取这个文本文件。不过我发现,如果我用记事本打开这个文本文件,在任何地方加一个空格并保存,Python就能正常工作了。

我在我的Mac上用同样的代码和文件试了一下,结果和Windows上遇到的问题一样。

对于原始的文本文件,无法读取;用Windows记事本打开并保存后,可以读取;用Mac的文本编辑器打开并保存后,还是无法读取。

我在怀疑这个文本文件的原始编码可能有问题。

谢谢

Python代码

InputFileName=input("Please tell me the input file name:")
#StartLNum=int(input("Please tell me the start line number:"))
#EndLNum=int(input("Please tell me the end line number:"))

StartLNum=18
EndLNum=129

lnum=1
OutputName='out'+InputFileName
fw=open(OutputName,'w')
with open(InputFileName,"r") as fr:
    for line in fr:
        if (lnum >= StartLNum) & (lnum<=EndLNum):
            #print(line)
            fw.write(line)
        lnum+=1
fw.close()

Shell

>>> ================================ RESTART ================================
>>> 
Please tell me the input file name:Jul-18-2014.txt
Traceback (most recent call last):
File "C:\Users\Jeremy\Desktop\read.py", line 13, in <module>
for line in fr:
UnicodeDecodeError: 'gbk' codec can't decode byte 0xb3 in position 4309: illegal multibyte sequence
>>> ================================ RESTART ================================
>>> 
Please tell me the input file name:Jul-18-2014.txt
>>> 

另外,下面的错误信息是我在Mac上(Python 3.4.1,OS 10.9)运行同样的代码时出现的。

Traceback (most recent call last):
File "/Users/Jeremy/Desktop/read.py", line 14, in <module>
for line in fr:
File "/Library/Frameworks/Python.framework/Versions/3.4/lib/python3.4/encodings/ascii.py",  line 26, in decode
return codecs.ascii_decode(input, self.errors)[0]
UnicodeDecodeError: 'ascii' codec can't decode byte 0xb3 in position 4174: ordinal not in range(128)

1 个回答

2

当你在记事本中保存文件时,这个文件会被重新编码,以便按照你Windows系统的默认文件编码来保存。不过,记事本在打开文件时会自动检测到编码方式。

Python默认也是用同样的系统编码来打开文件,这就是你现在可以打开这个文件的原因。引用一下open()函数的说明:

encoding是用来解码或编码文件的编码名称。这只应该在文本模式下使用。默认的编码方式依赖于平台(也就是locale.getpreferredencoding()返回的内容),但Python支持的任何编码都可以使用。

如果你想直接在Python中打开文件,你需要明确指定文件的正确编码:

with open(InputFileName, "r", encoding='utf-8-sig') as fr:

这里我用'utf-8-sig'作为例子,因为这是记事本可以自动检测到的一种文件编码。不过,文件的编码也可能是UTF-16、普通的UTF-8,或者其他很多种编码。

如果你认为这个页面使用了特定的ANSI代码页,你仍然需要准确地指定确切的代码页。你的系统配置使用的是936代码页(GBK),但这并不是这个文件的正确编码。

查看codecs模块,可以找到支持的编码列表。

撰写回答