如何用Python编码字符?

时间:2013-09-20 09:39:01

标签: python string encoding

来自Dive into Python

  

在Python 3中,所有字符串都是Unicode字符序列。没有用UTF-8编码的Python字符串或编码为CP-1252的Python字符串。 “这个字符串是UTF-8吗?”是一个无效的问题。 UTF-8是一种将字符编码为字节序列的方法。如果你想获取一个字符串并将其转换为特定字符编码中的字节序列,Python 3可以帮助你。如果你想获取一个字节序列并将其转换为字符串,Python 3也可以帮助你。字节不是字符;字节是字节。角色是一种抽象。字符串是这些抽象的序列。

我不明白作者的意思。

当我说s = 'hello'时,s如何在内部编码?当然它必须使用一些使用一些编码。他说所有字符串都是Unicode字符序列。但是每个字符有多少个字节?这个字符串是UTF-8吗?他为什么这样说:“没有用UTF-8编码的Python字符串”。

我理解Python提供了将Python“字符串”转换为一系列字节的功能,这些字节可由另一个使用该编码的软件读取。它还支持将一系列字节转换为Python“字符串”。现在,这个“字符串”的内部表示让我感到困惑。

3 个答案:

答案 0 :(得分:4)

作者比较Python 2和3中的字符串。在Python 2中,字符串表示为字节数组,因此在处理非ASCII字符时引入了许多问题。程序员必须始终跟踪其应用程序中字符串的当前编码(例如,HTML页面上的文本编码)。试图通过引入Unicode对象在Python 2.x中解决它:

s  = 'text'    # string/byte array object 
un = u'text'   # unicode object

但是许多应用仍然使用普通的旧式字符串。

因此,在Python 3中,决定将字符串(使它们都是Unicode)和字节数组分开。因此,在Python 3中我们有:

s = 'text'                             # string/unicode object
b = bytes([0xA2,0x01,0x02,0x03,0x04])  # byte array object

答案 1 :(得分:4)

  

当我说s ='hello'时,内部如何编码?当然它必须使用一些编码。

这取决于。坦率地说,没关系。 CPython现在使用Flexible String Representation,这是一个很棒的空间和时间优化。但你不应该在乎,因为它无所谓。

  

他说所有字符串都是Unicode字符序列。但是每个字符有多少字节?

说不上。这取决于。在这种特殊情况下,它可能处于Latin-1(1字节)(当使用CPython时)。

  

这个字符串是UTF-8吗?

没有

  

为什么他说:“没有用UTF-8编码的Python字符串”。

因为它是一系列Unicode代码点。如果您将编码与字符串混淆(因为其他语言通常强制您要这样做),您可能会认为'Jalape\xc3\xb1o''Jalapeño',因为在UTF-8中字节序列{ {1}}代表'\xc3\xb1o'。但事实并非如此,因为字符串没有内在编码,就像数字'ñ'是数字100而不是100一样,无论你是否用二进制代表它,小数或一元。

他说这是因为人们来自语言,他们只有字节代表字符串,他们认为“但这是如何编码的”,就像他们必须自己解码一样。这就像携带一个1和0的列表而不是能够使用数字,你必须告诉每个函数你正在使用什么字节序。

  

我理解Python提供了将Python“字符串”转换为一系列字节的功能,这些字节可由另一个使用该编码的软件读取。它还支持将一系列字节转换为Python“字符串”。现在,这个“字符串”的内部表示让我感到困惑。

希望它不再存在:)。


如果这让你感到困惑,我推荐this question,部分'因为有人称我的答案“非常全面”¹但也因为Steven D'Aprano已将他的一个Python邮件列表发布在那里 - 他和我从列表中回答并发布了我们的文字。

如果你想知道它为什么相关,我会引用:

  

所以你引用的人在谈到“编码字符串”时会引起混淆,他应该说清楚他是指一串字节,或者根本不提字词串。

难道这不是你的困惑吗?

¹从技术上讲,他称另一个答案是“另一个非常全面的答案”,但这意味着我刚才说的话。)。

答案 2 :(得分:0)

Python在内部对unicode字符串使用UCS-2或UCS-4编码(至少在Python 2.x中)。