与编码和解码混淆

2024-09-21 20:02:02 发布

您现在位置:Python中文网/ 问答频道 /正文

所以我想通过写字母的十六进制值来打印希伯来语(或任何其他语言),解码并打印到终端

这就是我尝试的,我从https://en.wikipedia.org/wiki/Code_page_862获得了cp862的代码页,并试图打印第一个字母。它输出其他东西,而不是想要的结果

我做错了什么

letter = b'\x05\xD0'
print(letter.decode('cp862'))

输出:

wahalez@wahalez:~/dev/python$python p25.py

我什么时候使用编码,什么时候使用解码

编辑:

另一个奇怪的行为是,我交换了字节并将其解码为utf-16,结果成功了。为什么

letter2 = b'\xD0\x05'
print(letter2.decode('utf-16'))

Tags: https语言终端字母解码utfenprint
3条回答

你误读了那张图表。值0x05D0是该字符的unicode代码点。值0x80是CP862值(请参见右侧的8_和顶部的_0)。所以如果你要写:

>>> letter = b'\x80'
>>> print(letter.decode('cp862'))
א

你会得到你想要的


how can I use the unicode instead ? and with what encoding ?

我不完全清楚你想做什么。如果只想使用表中的字符,可以复制并粘贴它。例如:

letter = 'א`

没有必要乱搞编码或解码

如果要从特定的unicode代码点生成字符,只需使用chr函数:

>>> print(chr(0x05d0))
א
  • 在python字符串中,字节和字节序列称为平面序列,这意味着它们被索引,但它们与容器化序列(如列表或元组)的类型不同
  • 任何字符串都有一个固定的标识,称为代码点 代码点是介于0和0到1114111之间的小数
  • 内置函数ord()使用单个字符并返回一个表示字符代码点的整数

print([chr(i) for i in range(100,120)])

['d', 'e', 'f', 'g', 'h', 'i', 'j', 'k', 'l', 'm', 'n', 'o', 'p', 'q', 'r', 's', 't', 'u', 'v', 'w']

ord('€')

8364

代码点的形式为U+前缀

字母A的代码点为U+0041,欧元符号为U+20AC

如果我们用hex()包装ord(),我们得到字符的十六进制表示

hex(ord('A'))

'0x41'

hex(ord('€'))

'0x20ac'

现在,如果你从机器的角度来考虑这一点,你会认为所有这些都是用机器语言写的。因此,您需要使用机器语言将其转换为用户可以阅读的格式

b'\x41'.decode('UTF_8')

'A'

b'\x41\x00'.decode('UTF_16')

'A'

b'\x41'和b'\x41\x00'是utf-8和utf-16编码中字母A的字节序列

b'\xe2\x82\xac'.decode('UTF_8')

'€'

b'\xac\x20'.decode('UTF_16')

'€'

当你编码时,你正在把一个字节序列转换回机器能理解的语言

字节序列是机器识别的代码点表示形式 我们

.encode()字符串为字节,.decode()字节为字符串

字符串和字节之间的映射使用UTF-8(或UTF-16,gb2312…)编码进行解释

"café".encode('utf_8')

b'caf\xc3\xa9'

"café".encode('utf_16')

b'\xff\xfec\x00a\x00f\x00\xe9\x00'

'El Niño'.encode('utf_8')

b'El Ni\xc3\xb1o'

因此,当实例对象是希伯来语或字符时使用.encode(),当实例是字节序列时使用.decode(),例如字母a的字节序列b'\x41\x00'

在一个非常相似的行为中,类方法bytes()接收字符并将它们像.encode()一样编码为字节序列

bytes("El Niño", encoding = 'utf_16')

b'\xff\xfeE\x00l\x00 \x00N\x00i\x00\xf1\x00o\x00'

上面的所有代码都在python3.8中。在Python2中,数据类型是不同的。因此,如果您在python 2中尝试此操作,请务必小心

有一个方便的缩写;坏蛋:字节被解码,文本被编码

此外,您还将Unicode代码点与cp862值混淆

希伯来文字母Aleph是Unicode代码点0x05D0,但在代码页862中是0x80

试试这个:

In [3]: b = b'\x80'
Out[3]: b'\x80'

In [4]: b.decode('cp862')
Out[4]: 'א'

要使用unicode代码点,请尝试:

In [12]: chr(0x05D0)
Out[12]: 'א'

相关问题 更多 >