Why do I need 'b' to encode a string with Base64?
在此python示例之后,我将字符串编码为Base64:
1 2 3 4 | >>> import base64 >>> encoded = base64.b64encode(b'data to be encoded') >>> encoded b'ZGF0YSB0byBiZSBlbmNvZGVk' |
但是,如果我省略前导
1 | >>> encoded = base64.b64encode('data to be encoded') |
我收到以下错误:
1 2 3 4 5 | Traceback (most recent call last): File"<stdin>", line 1, in <module> File"C:\Python32\lib\base64.py", line 56, in b64encode raise TypeError("expected bytes, not %s" % s.__class__.__name__) TypeError: expected bytes, not str |
为什么是这样?
base64编码采用8位二进制字节数据,并且仅使用字符
因此,它需要一个8位字节的字符串。您可以使用
如果删除
在第二个示例中:
1 | >>> encoded = base64.b64encode('data to be encoded') |
所有字符都完全适合ASCII字符集,因此base64编码实际上是没有意义的。您可以将其转换为ascii
1 | >>> encoded = 'data to be encoded'.encode('ascii') |
或更简单:
1 | >>> encoded = b'data to be encoded' |
在这种情况下,这将是同一件事。
*大多数base64口味的末尾也可能包含
简短答案
您需要将
1 2 3 | >>> data = base64.b64encode(b'data to be encoded') >>> print(data) b'ZGF0YSB0byBiZSBlbmNvZGVk' |
或带有变量:
1 2 3 4 | >>> string = 'data to be encoded' >>> data = base64.b64encode(string.encode()) >>> print(data) b'ZGF0YSB0byBiZSBlbmNvZGVk' |
为什么?
在Python 3中,
Python 3中的Base-64编码
最初,问题标题是关于Base-64编码的。继续阅读有关Base-64的内容。
在
例:
1 2 3 4 5 6 | >>> data = b'test' >>> for byte in data: ... print(format(byte, '08b'), end="") ... 01110100 01100101 01110011 01110100 >>> |
如果您将二进制数据解释为单个整数,则可以通过以下方法将其转换为base-10和base-64(base-64表):
1 2 3 | base-2: 01 110100 011001 010111 001101 110100 (base-64 grouping shown) base-10: 1952805748 base-64: B 0 Z X N 0 |
但是,
1 2 3 | base-2: 011101 000110 010101 110011 011101 00(0000) <- pad w/zeros to make a clean 6-bit chunk base-10: 29 6 21 51 29 0 base-64: d G V z d A |
因此,从数学上来说," B0ZXN0"是我们二进制文件的base-64版本。但是,
让我们测试一下,看看我是否不诚实:
1 2 3 | >>> encoded = base64.b64encode(data) >>> print(encoded) b'dGVzdA==' |
为什么使用
假设我必须通过电子邮件将某些数据发送给某人,例如以下数据:
1 2 3 4 5 6 | >>> data = b'\x04\x6d\x73\x67\x08\x08\x08\x20\x20\x20' >>> print(data.decode()) >>> print(data) b'\x04msg\x08\x08\x08 ' >>> |
我植入了两个问题:
这只是一个演示,向您展示简单发送原始数据有多困难。将数据编码为base64格式可为您提供完全相同的数据,但格式应确保可以安全地通过电子媒体(例如电子邮件)发送。
如果要编码的数据包含"外来"字符,我认为您必须使用" UTF-8"进行编码
1 | encoded = base64.b64encode (bytes('data to be encoded',"utf-8")) |
如果字符串是Unicode,最简单的方法是:
1 2 3 4 5 6 7 8 9 10 | import base64 a = base64.b64encode(bytes(u'complex string: ?áéíóú?',"utf-8")) # a: b'Y29tcGxleCBzdHJpbmc6IMOxw6HDqcOtw7PDusOR' b = base64.b64decode(a).decode("utf-8","ignore") print(b) # b :complex string: ?áéíóú? |
有您需要的一切:
1 | expected bytes, not str |
前导
您使用什么版本的Python? 2.x或3.x?
编辑:请参阅http://docs.python.org/release/3.0.1/whatsnew/3.0.html#text-vs-data-instead-of-unicode-vs-8位了解Python中字符串的详细信息3.x
b只是意味着您将输入作为字节或字节数组而不是字符串。