gpt4 book ai didi

python - sys.setdefaultencoding ('utf-8' 的危险)

转载 作者:行者123 更新时间:2023-12-02 19:13:51 27 4
gpt4 key购买 nike

有劝阻设置的趋势sys.setdefaultencoding('utf-8')在 Python 2 中。任何人都可以列出有关问题的真实示例吗?像 it is harmful 这样的参数或 it hides bugs听起来不太有说服力。

更新 : 请注意这个问题只是关于utf-8 ,这与“在一般情况下”更改默认编码无关。

如果可以的话,请给出一些带有代码的例子。

最佳答案

因为您并不总是希望将字符串自动解码为 Unicode,或者就此而言,您的 Unicode 对象会自动编码为字节。由于您要求一个具体的例子,这里有一个:

拿一个 WSGI Web 应用程序;您正在通过在循环中将外部进程的产品添加到列表中来构建响应,并且该外部进程为您提供 UTF-8 编码字节:

results = []
content_length = 0

for somevar in some_iterable:
output = some_process_that_produces_utf8(somevar)
content_length += len(output)
results.append(output)

headers = {
'Content-Length': str(content_length),
'Content-Type': 'text/html; charset=utf8',
}
start_response(200, headers)
return results

这很好,很好,很有效。但是随后您的同事出现并添加了新功能;您现在也提供标签,这些标签已本地化:
results = []
content_length = 0

for somevar in some_iterable:
label = translations.get_label(somevar)
output = some_process_that_produces_utf8(somevar)

content_length += len(label) + len(output) + 1
results.append(label + '\n')
results.append(output)

headers = {
'Content-Length': str(content_length),
'Content-Type': 'text/html; charset=utf8',
}
start_response(200, headers)
return results

你用英语测试了这个,一切仍然有效,太棒了!

但是, translations.get_label()库实际上返回 Unicode 值 并且当您切换区域设置时,标签包含非 ASCII 字符。

WSGI 库将这些结果写入套接字,并且所有 Unicode 值都会为您自动编码,因为您设置了 setdefaultencoding()到 UTF-8,但你计算的长度是完全错误的。它太短了,因为 UTF-8 将 ASCII 范围之外的所有内容都编码为一个字节以上。

所有这些都忽略了您实际上正在使用不同编解码器中的数据的可能性;你可能正在写出 Latin-1 + Unicode,现在你有一个不正确的长度标题和混合的数据编码。

如果你没用过 sys.setdefaultencoding()会引发异常并且您知道自己有错误,但现在您的客户提示响应不完整;页面末尾缺少字节,您不太清楚这是怎么发生的。

请注意,这种情况甚至不涉及可能依赖或不依赖于默认仍然是 ASCII 的 3rd 方库。 sys.setdefaultencoding()设置是全局的,适用于 全部 在解释器中运行的代码。您有多确定在那些涉及隐式编码或解码的库中没有问题?

Python 2 在 str 之间进行编码和解码和 unicode仅在处理 ASCII 数据时,隐式类型会很有帮助且安全。但是你真的需要知道你什么时候不小心混合了 Unicode 和字节字符串数据,而不是用全局刷子涂抹它并希望最好。

关于python - sys.setdefaultencoding ('utf-8' 的危险),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/28657010/

27 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com