我正在努力将一个大型项目从python2
转换为python3
(不需要python2
向后兼容性)。
在测试转换时,我发现我遇到了一个问题,即某些字符串正在转换为bytes
对象,这导致了麻烦。我将其追溯到以下方法,该方法在很多地方被调用:
def custom_format(val):
return val.encode('utf8').strip().upper()
在python2
:
custom_format(u'xa0')
# 'xc2xa0'
custom_format('bar')
# `BAR`
在python3
:
custom_format('xa0')
# b'xc2xa0'
custom_format('bar')
# b`BAR`
这是一个问题的原因是,在某些时候,custom_format
的输出应该使用format()
但'foo = {}'.format(b'bar') == "foo = b'BAR'"
插入到SQL
模板字符串中,这会弄乱潜在的SQL
语法。
简单地删除encode('utf8')
部分将确保custom_format('bar')
正确返回'BAR'
,但现在custom_format('xa0')
返回'xa0'
而不是python2
版本的'xc2xa0'
。(虽然我对 unicode 的了解还不够多,不知道这是否是一件坏事)
在不弄乱代码的SQL
或format()
部分的情况下,如何确保python2
版本的预期行为在python3
版本中显示?是像放弃encode('utf8')
那么简单,还是会导致意外冲突?
如果你的目的是确保所有传入的字符串,无论是str
还是bytes
,都被转换为bytes
,那么你必须保持encode
,因为Python3使用str
而不是bytes
(Python2就是这种情况)作为本机字符串类型。encode
将str
转换为bytes
。
如果您的目的是确保查询看起来正确。然后你可以删除encode
,让Python3为你处理事情。