我来梳理一下吧:
首先 requests 里关于获取编码的几个函数:
1. `get_encodings_from_content`:
utils.py 中定义,譬如从 HTML head 的 meta 中获取 charset
2. `get_encoding_from_headers`:从响应头的 Content-Type 来猜测
3. `chardet.detect`: 编码自动检测工具
然后 requests 处理编码方式的流程是这样的:
1. 首先看响应头的 Content-Type 里是否包含 charset,有就设置并返回
2. 若 Content-Type 里没有 charset,但是 MIME 是 text/*,则直接设置编码为 ISO-8859-1 (这一点 requests 是为了遵循 RFC2616/3.7.1 )
3. 当第 1、2 点都不符合时,encoding 为空,才使用 chardet.detect 自动检测
**问题所在**:
第二点导致国内很多网站的编码方式被认为是 ISO-8859-1,在西方国家,没啥大问题。但是在亚洲很多国家,将会出现乱码
具体讨论可以看:
https://github.com/requests/requests/issues/1604PS:
1. 好像 RFC2616 中将默认编码设为 ISO-8859-1 已经被弃用了。然后 requests 上关于这个问题貌似还在讨论...(
https://github.com/requests/requests/issues/2086 )
2. 很多人可能会疑问,为什么 requests 处理编码问题里没有用`get_encodings_from_content`,Lukasa 解释是这样的:
> Our position on this has been that we're not a HTML library, we're a HTTP library, and therefore examining the body of the request is outside our remit.
当然,你可以自行调用嘛:
```
import requests
from requests.utils import get_encodings_from_content
r = requests.get('
http://baike.baidu.com/view/115789.htm')
codings = get_encodings_from_content(r.content)
if codings:
r.encoding = codings[0]
```