TLDR? Thử:file = open(filename, encoding='cp437)
Tại sao? Khi một người sử dụng:
file = open(filename)
text = file.read()
Python giả định tệp sử dụng cùng một bảng mã như môi trường hiện tại (cp1252 trong trường hợp bài đăng mở) và cố gắng giải mã nó thành UTF-8 mặc định của chính nó. Nếu tệp chứa các ký tự của các giá trị không được xác định trong bảng mã này (như 0x90), chúng tôi sẽ nhận được UnicodeDecodeError. Đôi khi chúng ta không biết mã hóa tệp, đôi khi mã hóa của tệp có thể được xử lý bởi Python (ví dụ: cp790), đôi khi tệp có thể chứa mã hóa hỗn hợp.
Nếu các ký tự đó không cần thiết, người ta có thể quyết định thay thế chúng bằng dấu chấm hỏi, bằng:
file = open(filename, errors='replace')
Một cách giải quyết khác là sử dụng:
file = open(filename, errors='ignore')
Các ký tự sau đó được giữ nguyên, nhưng các lỗi khác cũng sẽ bị che đi.
Giải pháp khá tốt là chỉ định mã hóa, nhưng không phải bất kỳ mã hóa nào (như cp1252), nhưng mã hóa có TẤT CẢ các ký tự được xác định (như cp437):
file = open(filename, encoding='cp437')
Codepage 437 là mã hóa DOS gốc. Tất cả các mã được xác định, do đó không có lỗi trong khi đọc tệp, không có lỗi được che dấu, các ký tự được giữ nguyên (không còn nguyên vẹn nhưng vẫn có thể phân biệt được).