zoukankan      html  css  js  c++  java
  • Python 2.x and 3.x String VS Bytes

    In Python 3 unicode strings are the 'regular strings' (str) and byte strings are separate objects.

    Low level I/O can be done only with data (byte strings), not text (sequence of characters). For Python 2.x str was also the 'binary data' type. In Python 3 it is not any more and one of the special 'data' objects should be used. Objects are pickled to such byte strings. If you want to enter them manually in code use the "b" prefix (b"XXX" instead of "XXX").

    bytes和string并不是毫无关系的,bytes对象有一个decode()方法,向该方法传递一个字符编码参数,该方法会返回使用该种编码解码后的字符串。同样的,string有一个encode()方法,完成反向的工作。

    图片出自:http://www.ituring.com.cn/article/1116


     一篇更详细的关于bytes VS string

    http://sebug.net/paper/books/dive-into-python3/strings.html

    以下内容摘录自上面的文章 


    字节即字节;字符是一种抽象。

    一个不可变(immutable)的Unicode编码的字符序列叫做string

    一串由0到255之间的数字组成的序列叫做bytes对象。

    >>> by = b'abcdx65'  (1)  
    >>> by
    b'abcde'
    >>> type(by)          (2)          
    <class 'bytes'>
    >>> len(by)           (3)
    5
    >>> by += b'xff'     (4)  
    >>> by
    b'abcdexff'
    >>> len(by)           (5)      
    6
    >>> by[0]             (6)   
    97
    >>> by[0] = 102       (7)  
    Traceback (most recent call last):
      File "<stdin>", line 1, in <module>
    TypeError: 'bytes' object does not support item assignment

    ① 使用“byte字面值”语法b''来定义bytes对象。byte字面值里的每个字节可以是ascii字符或者是从x00到xff编码了的16进制数。
    ② bytes对象的类型是bytes。
    ③ 跟列表和字符串一样,我们可以通过内置函数len()来获得bytes对象的长度。
    ④ 使用+操作符可以连接bytes对象。操作的结果是一个新的bytes对象。
    ⑤ 连接5个字节的和1个字节的bytes对象会返回一个6字节的bytes对象。
    ⑥ 一如列表和字符串,可以使用下标记号来获取bytes对象中的单个字节。对字符串做这种操作获得的元素仍为字符串,而对bytes对象做这种操作的返回值则为整数。确切地说,是0–255之间的整数。
    ⑦ bytes对象是不可变的;我们不可以给单个字节赋上新值。如果需要改变某个字节,可以组合使用字符串的切片和连接操作(效果跟字符串是一样的),或者我们也可以将bytes对象转换为bytearray对象。

    >>> by = b'abcdx65'
    >>> barr = bytearray(by)  (1)
    >>> barr
    bytearray(b'abcde')
    >>> len(barr)             (2)
    5
    >>> barr[0] = 102         (3)
    >>> barr
    bytearray(b'fbcde')

    ① 使用内置函数bytearray()来完成从bytes对象到可变的bytearray对象的转换。
    ② 所有对bytes对象的操作也可以用在bytearray对象上。
    ③ 有一点不同的就是,我们可以使用下标标记给bytearray对象的某个字节赋值。并且,这个值必须是0–255之间的一个整数。

    我们决不应该这样混用bytes和strings。

    >>> by = b'd'
    >>> s = 'abcde'
    >>> by + s                                        (1)                  
    Traceback (most recent call last):
      File "<stdin>", line 1, in <module>
    TypeError: can't concat bytes to str
    >>> s.count(by)                                   (2)
    Traceback (most recent call last):
      File "<stdin>", line 1, in <module>
    TypeError: Can't convert 'bytes' object to str implicitly
    >>> s.count(by.decode('ascii'))                   (3)
    1

    ① 不能连接bytes对象和字符串。他们两种不同的数据类型。
    ② 也不允许针对字符串中bytes对象的出现次数进行计数,因为串里面根本没有bytes。字符串是一系列的字符序列。也许你是想要先把这些字节序列通过某种编码方式进行解码获得字符串,然后对该字符串进行计数?可以,但是需要显式地指明它。Python 3不会隐含地将bytes转换成字符串,或者进行相反的操作。
    ③ 好巧啊…这一行代码刚好给我们演示了使用特定编码方式将bytes对象转换成字符串后该串的出现次数。

    所以,这就是字符串与字节数组之间的联系了:bytes对象有一个decode()方法,它使用某种字符编码作为参数,然后依照这种编码方式将bytes对象转换为字符串,对应地,字符串有一个encode()方法,它也使用某种字符编码作为参数,然后依照它将串转换为bytes对象。在上一个例子中,解码的过程相对直观一些 — 使用ascii编码将一个字节序列转换为字符串。同样的过程对其他的编码方式依然有效 — 传统的(非Unicode)编码方式也可以,只要它们能够编码串中的所有字符。

    >>> a_string = '深入 Python'          (1)
    >>> len(a_string)
    9
    >>> by = a_string.encode('utf-8')    (2)
    >>> by
    b'xe6xb7xb1xe5x85xa5 Python'
    >>> len(by)
    13
    >>> by = a_string.encode('gb18030')  (3)
    >>> by
    b'xc9xeexc8xeb Python'
    >>> len(by)
    11
    >>> by = a_string.encode('big5')      (4)
    >>> by
    b'xb2`xa4J Python'
    >>> len(by)
    11
    >>> roundtrip = by.decode('big5')     (5) 
    >>> roundtrip
    '深入 Python'
    >>> a_string == roundtrip
    True


    ① a_string是一个字符串。它有9个字符。
    ② by是一个bytes对象。它有13个字节。它是通过a_string使用utf-8编码而得到的一串字节序列。
    ③ by还是一个bytes对象。它有11个字节。它是通过a_string使用GB18030编码而得到的一串字节序列。
    ④ 此时的by仍旧是一个bytes对象,由11个字节组成。它又是一种完全不同的字节序列,我们通过对a_string使用Big5编码得到。
    ⑤ roundtrip是一个字符串,共有9个字符。它是通过对by使用Big5解码算法得到的一个字符序列。并且,从执行结果可以看出,roundtrip与a_string是完全一样的。

  • 相关阅读:
    基于LBS(GPS)和ArcGIS的ITS智能交通 路况服务架构
    入手ipod touch4
    改2字节将Win XP Home变成Pro?!(zz)
    越来越多的同学在MSN上建Blog了……
    有了64位的芯不一定能运行64位OS?(zz)
    C++字符串完全指引之二——字符串封装类(zz)
    忙……
    注意C#中的ref及out关键字
    期待CGFTP 1.0正式版:)
    真伪双核 英特尔双核平台深度揭秘(zz)
  • 原文地址:https://www.cnblogs.com/AlexBai326/p/4063172.html
Copyright © 2011-2022 走看看