Python:数据与文本?

时间:2009-11-15 01:13:20

标签: python unicode python-3.x

Guido van Rossum关于Python 3000的演讲最后提到了从Python 2到Python 3过渡的几个方面。他特别谈到自从转移到Unicode以来的文本处理,因为Python 3中字符串的唯一表示是主要变化之一。

就文本处理而言,一张幻灯片(#14)说:

  • 在2.6中:
    • 对所有数据使用字节和b'...'(知道这些只是str和'...'的别名)
    • 对所有文字使用unicode和u'...'
  • 在2.5中:
    • '...'表示数据,u'...'表示文字

我正在使用Python 2.6.4。这究竟对我意味着什么?

在Python世界中,数据和文本之间有什么区别?

2 个答案:

答案 0 :(得分:18)

简而言之,在Py3k中处理文本和数据的方式可能是语言中最“突破”的变化。通过在可能的情况下了解并避免某些Python 2.6逻辑与3.x中的工作方式不同的情况,我们可以在发生迁移时促进迁移。然而,我们应该期望2.6逻辑的某些部分可能需要特别注意和修改,例如处理不同的编码等。

BDFL对幻灯片14的建议背后的想法可能是开始“使用”与Py3k支持的相同类型(仅限于这些),即字符串的unicode字符串(str类型)和“数据”(bytes类型)的8位字节序列。

上一句中的术语“ using ”使用相当松散,因为这些类型的语义和相关存储/编码在2.6和3.x版本之间不同。在Python 2.6中,字节类型和相关的文字语法(b'xyz')只是映射到str类型。因此

# in Py2.6
>>'mykey' == b'mykey'
True
b'mykey'.__class__
<class 'str'>

# in Py3k
>>>'mykey' == b'mykey'
False
b'mykey'.__class__
<class 'bytes'>  

要回答你的问题[在下面的评论中],在2.6中你是否使用b'xyz'或'xyz',Python将其理解为同一个东西:str。 重要的是将这些理解为[潜在/未来]两种截然不同的类型

  • str表示类似文本的信息,
  • 用于存储手头数据的八位字节序列的字节。

例如,再说一下您的示例/问题,在Py3k中,您将能够拥有一个包含两个具有相似键的元素的字典,一个使用b'mykey',另一个使用'mykey',但是2.6以下这是不可能的,因为这两个键真的是一样的;重要的是你知道这种事情并避免(或在代码中以特殊方式明确标记)2.6代码在3.x中不起作用的情况。

在Py3k中,str是一个抽象的unicode字符串,一系列unicode代码点(字符)和Python处理将其转换为编码形式或从编码形式转换(无论编码可能是什么)(作为程序员,你对编码,但在你处理字符串操作时,你不需要担心这些细节)。相反,字节是一个8位“事物”的序列,语义和编码完全留给程序员。

所以,即使Python 2.6没有看到区别,通过显式使用bytes()/ b'...'或str()/ u'...',你......

  • ...为即将到来的Py3k类型和语义准备好自己和你的程序
  • ...使源代码的自动转换(2to3工具或其他)变得更容易,其中b'...'中的b将保留,并且u'...'的u将被删除(因为唯一的字符串类型是unicode)。

了解更多信息
Python 2.6 What's new(参见PEP 3112 Bytes Literals)
Python 3.0 What's New(请参阅顶部附近的Text Vs. Data Instead Of Unicode Vs. 8-bit

答案 1 :(得分:2)

你的第一个问题的答案很简单:在Python 2.6中你可以做到。但是,如果您愿意,可以通过输入以下内容切换到Py3k标准:

from __future__ import unicode_literals

您的第二个问题需要进一步澄清:

字符串是作为人物角色打印的数据。不仅在Python中,而且在处理字符串时,每种语言(我都知道)都有它的方法。

然而,共同点是编码。编码是将字节序列映射到字形的方式(即主要是可打印的符号)。

Python提供了一种简单的方法来克服管理编码的复杂性(当您在代码中放入字符串文字时)。

让我们看一个非常简单的例子:

>>> len("Mañana")
7

我只看到6个符号。所以我希望len会返回6.这个额外的“符号”来自哪里?在UTF-8中,符号ñ用2个字节表示。在Py3k之前,字符串文字只是字节序列。因此,Python将该字符串视为字节,并将它们全部计算在内:Ma\xc3\xb1ana

但是,如果我执行以下内容:

>>> len(u"Mañana")
6

因此Python“确切地”知道“ñ”的2字节序列被视为单个字母。

这绝不是Python独有的。以下PHP脚本显示相同的行为:

manu@pavla:~$ php <<EOF
<?php
echo strlen("Mañana")."\n";
?>
EOF
7

PHP解决方案恰好更精细:

manu@pavla:~$ php <<EOF
<?php
echo mb_strlen("Mañana", "utf-8")."\n";
?>
EOF
6

请注意,我必须将mb_strlen替换为strlen,我必须将utf-8(编码)作为第二个参数传递。

警告:用户提供的字符串通常是字节,而不是unicode字符串。所以你需要照顾它。有关http://mail.python.org/pipermail/python-list/2008-July/139193.html

的更多信息,请参阅