字符编码及字节串bytes类型

我不是女神ヾ 2023-06-04 11:55 67阅读 0赞

1 字符编码简介

  ASCII码:美国人发明并使用,用1个字节(8位二进制)代表一个字符,ASCII码是其他任意编码表的子集(utf-16除外).

  Unicode:包含和兼容全世界的语言,与全世界的语言都有映射关系,常用2个字节表示一个字符,1个生僻字用4个字节表示.

  utf-8:可变长编码,英文用1个字节表示,汉字通常是3个字节,生僻字常用4-6个字节表示,uft-8比Unicode编码节省空间和I/O开销.

  关于Unicode和utf-x格式之间的关系,可以认为utf-x是Unicode的一种特殊类型,在存取数据时,内部会自动在Unicode和utf-x之间转换.

  在内存中,统一使用的都是Unicode编码(固定,集成在操作系统中),所以可以转换为任意其他国家自定义的编码(这样就不会乱码);在将数据存入硬盘时,需要将Unicode转换为一种更精准的格式,即utf-8,将数据控制在最精准和节省空间;而磁盘数据读入缓存到内存中时,则需要将utf-8转换为Unicode.

  在python2.x中,默认使用ASCII编码作为字符编码;而在python3.x中,默认使用Unicode作为默认字符编码.

  1. import sys
  2. print(sys.getdefaultencoding())
  3. 'ascii' #python2.x默认字符编码
  4. ---------------------------------
  5. import sys
  6. print(sys.getdefaultencoding())
  7. 'utf-8' #python3.x默认字符编码 
  8. ---------------------------------
  9. U=u'阿凡达' #3*3=9字节,8*9=72bytes
  10. U1=bytes(U,'utf-8')
  11. print(U1) # 构造Unicode字符,结果是 b'\xe9\x98\xbf\xe5\x87\xa1\xe8\xbe\xbe',\x代表16进制存储,1个字符代表4byte,18*4=72bytes

1.1 字符编码和解码

  两张图读懂字符编码与解码之间的关系,编码和解码对应,就不会出现乱码了,参考资料及图片来源:

  https://www.cnblogs.com/f-ck-need-u/p/10185965.html

  https://www.cnblogs.com/linhaifeng/articles/5950339.html

1555421-20190911162245884-1320682640.png

1555421-20190911161712811-991350937.png

  1. 编码: str ---> bytes (encode)
  2. 解码: bytes ---> str (decode)
  3. 二进制格式的数据也常称为裸数据(raw data),str数据经过编码后得到raw dataraw data解码后得到的str.
  4. 内存中是unicode-------->encode编码保存-------->utf-8保存到磁盘(二进制)
  5. utf-8磁盘里保存-------->decode解码缓存到内存中---------->unicode内存中
  6. 注意: 编码和解码的过程中,与软件指定的编码(字符集)也有关系,必须对应.
  7. ######################
  8. print((set(dir(str)))-set(dir(bytes))) #字符串类型只有编码encode()方法,没有解码decode()
  9. print((set(dir(bytes)))-set(dir(str))) #字节串类型只有解码decode()方法,没有编码encode()
  10. --------------------
  11. {'format', 'isdecimal', 'casefold', 'format_map', 'isidentifier', 'isnumeric', 'isprintable', 'encode'}
  12. {'hex', 'decode', 'fromhex'}

1.2 str,bytes,bytearray类型

  str:字符串类型,有序有索引,序列数据,可以迭代取值,但属于不可变类型,底层存储由一个个二进制组成,也就是bytes.python3.x中str默认是Unicode(uft-8)格式编码.

  bytes:字节串类型,二进制字节数据,有序有索引,序列数据,可以迭代取值,也属于不可变类型;将字符串数据存到硬盘的的过程,实质上就是将Unicode转换为utf-8下的二进制字节这样就可以往硬盘存数据(二进制转换为十六进制存),或通过网络方式传输到其他地方.

  bytearray:可变的字节串类型,属于可变的二进制数据(bytes),属于可变类型.

  1. import sys                #python3.x下查看默认字符编码为 utf-8
  2. print(sys.getdefaultencoding()) #结果是 utf-8
  3. ----------------------------
  4. B=b'aaa'
  5. print(type(B),B)     #构造bytes类型,需在字符串前加 b ,结果是<class 'bytes'> b'aaa'
  6. ----------------------------
  7. B=b'aaa'         # 构造bytearray类型及改值
  8. By=bytearray(B)
  9. print(type(By),By)
  10. print(list(i for i in By))
  11. By[0]=98            #改值
  12. print(By)           #By=b'baa',a子串值已改变
  13. -------构造bytearray结果
  14. <class 'bytearray'> bytearray(b'aaa')
  15. [97, 97, 97]
  16. bytearray(b'baa')

1.3 乱码的原因及解决办法

  文件从内存写到硬盘的操作简称存文件,文件从硬盘读到内存的操作简称读文件.

  乱码的原因:

  1)存文件时就已经乱码(编辑的字符和编辑器设定保存的字符编码不一致)
  2)存文件时不乱码而读文件时乱码(存时的文件字符编码和读时编辑器设定的字符编码不对应)

  解决乱码的办法: 字符按照什么标准而编码的,就要按照什么标准解码,即编码和解码对应.

1555421-20190911165531472-41237087.png

1.4 python文件头指定字符编码

  为了避免乱码,在python文件中指定解释器和文件头也是一种方法,文件头指定的编码必须跟python文件存储时用的编码一致.

  1. #!/usr/bin/env python <===指定解释器(限linux)
  2. # -*- coding: utf-8 -*- <===指定字符编码(等同于#coding:utf-8)来将数据读入内存,由python解释器解释执行用的字符编码

  

  

转载于:https://www.cnblogs.com/blog-tim/p/11507947.html

发表评论

表情:
评论列表 (有 0 条评论,67人围观)

还没有评论,来说两句吧...

相关阅读

    相关 字符字节编码

    引言 “字符与编码”是一个被经常讨论的话题。即使这样,时常出现的乱码仍然困扰着大家。虽然我们有很多的办法可以用来消除乱码,但我们并不一定理解这些办法的内在原理。而有的乱码

    相关 字符字节编码

    级别:中级 摘要:本文介绍了字符与编码的发展过程,相关概念的正确理解。举例说明了一些实际应用中,编码的实现方法。然后,本文讲述了通常对字符与编码的几种误解,由于这些误解而导致