摘要:如果統一規定每個字符用個或者個字節來存儲,那么每個英文字符都必然需要額外到個,這對存儲是很大的浪費。因此對于英語字母,編碼和碼是相同的。中文中文輸出這里同樣可以知道,中存放的是文件保存的編碼的碼。
unicode 與 utf-8 的關系 unicode 是 character set
character set 是把每個字符對應成數字的集合,比如unicode中 A對應0041,漢字『我』對應 "6211"
unicode 是個很大的集合,幾乎覆蓋世界上所有的字符,現在的規模已經可以容納100萬個字符。
utf-8 是對 unicode 存儲的實現方式unicode 只定義字符對應的數字,但沒有規定這些數字如何存儲起來,比如像中文的『我』字存儲時需要兩個字節來表示,而英文字母A卻只需要一個字節,有些其他的字符可能需要3-4個字節。
如果統一規定每個字符用3個或者4個字節來存儲,那么每個英文字符都必然需要額外2到3個0,這對存儲是很大的浪費。
如果每個字符按照實際需要的字節數來存儲,計算機就分不清三個字節是表示三個字符還是一個字符。
utf-8 是對 unicode 編碼存儲的一種實現方式,同樣的還有 utf-16, utf-32。
utf-8 是使用最廣泛的編碼方式,采用變長的編碼方式,可以使用1-4個字節來表示一個字符; utf-16 用2個或4個字節,utf-32 用4個字節表示。編碼規則如下:
對于單字節的符號,字節的第一位設為0,后面7位為這個符號的unicode碼。因此對于英語字母, UTF-8編碼和ASCII碼是相同的。
對于n字節的符號(n>1),第一個字節的前n位都設為1,第n+1位設為0,后面字節的前兩位一律設為10。剩下的沒有提及的二進制位,全部為這個符號的unicode碼。
python2 中的 str 和 unicodepython2 中有字符串類型有兩種:byte string (str)和 unicode string (unicode)。
>>> s = "美的" >>> s "xe7xbex8exe7x9ax84" >>> s = u"美的" >>> s u"u7f8eu7684" >>> s = "美的" >>> s.decode("utf-8") u"u7f8eu7684"
上面的輸出中,第一個s的類型是 str,打印出來的內容是 utf-8 編碼過的內容。第二個s的類型是 unicode,打印出來的兩個雙字節的數字分別表示了兩個漢字『美的』。
encode和decode提供 str 和 unicode 這兩種的類型的互相轉化。
encode 把 unicode 轉化成 str(byte string)
decode 把 str(byte string) 轉化成 unicode
本質上,str是存放的字節序,有可能是 ascii, gbk, utf-8 等等中的任意一種,通過調用 decode 可以把他們轉化成 unicode ,默認的 decode 編碼是 ascii 。str中到底是用的哪一種編碼,取決于它所在的場景,跟 locale ,文件編碼等等都有關系。
文本文件、編輯器的處理#!/usr/bin/env python # -*- coding: GBK -*- s = u"中文" print repr(s) print repr(s.encode("GBK"))
比如上面的文件enc.py,保存的時候選擇文件編碼是GBK,程序文件本質上也是文件,當我們使用某個外部的應用 打開它時(編輯器或者python解釋器等),外部應用是不知道該文件的編碼格式的,
這個時候有三種情況:
應用使用其默認的編碼方式去解析,比如UTF-8或者ASCII;python解釋器默認是ASCII,編輯器可以自己設置;
應用根據文件中的字節內容,自動檢測編碼方式;
文本文件告訴應用使用什么編碼方式去解碼;比如# -*- coding: GBK -*-告知解釋器使用GBK來解碼;
試驗一下,把# -*- coding: GBK -*-刪除后,執行python enc.py,輸出:
File "enc.py", line 4 SyntaxError: Non-ASCII character "xd6" in file enc.py on line 4, but no encoding declared;
試著用vim打開該文件時,『中文』兩個字就會顯示成亂碼,因為vim默認的文件編碼方式被設置成UTF-8了。
#!/usr/bin/env python # -*- coding: GBK -*- s1 = u"中文" print repr(s1) print repr(s1.encode("GBK")) s2 = "中文" print repr(s2) print repr(s2.decode("GBK"))
輸出結果:
u"u4e2du6587" "xd6xd0xcexc4" "xd6xd0xcexc4" u"u4e2du6587"
從這里可以看出來, s2中存放的是byte格式的從文件中讀到的GBK編碼的內容。
再看下面的這段代碼,程序文件utf8_enc.py,保存成UTF-8編碼的。
#!/usr/bin/env python # -*- coding: utf-8 -*- s1 = u"中文" print repr(s1) print repr(s1.encode("GBK")) s2 = "中文" print repr(s2) print repr(s2.decode("GBK"))
輸出:
u"u4e2du6587" "xd6xd0xcexc4" "xe4xb8xadxe6x96x87" Traceback (most recent call last): File "unicode_enc.py", line 12, inprint repr(s2.decode("GBK")) UnicodeDecodeError: "gbk" codec can"t decode bytes in position 2-3: illegal multibyte sequence
這里同樣可以知道,s2中存放的是文件保存的編碼UTF-8的byte碼。
Referenceshttp://www.rrn.dk/the-differe...
http://www.ruanyifeng.com/blo...
https://docs.python.org/2/how...
http://yergler.net/2012/bytes...
文章版權歸作者所有,未經允許請勿轉載,若此文章存在違規行為,您可以聯系管理員刪除。
轉載請注明本文地址:http://specialneedsforspecialkids.com/yun/38215.html
摘要:最近使用處理一些網絡相關的問題,被相關的一系列編碼問題搞得一頭霧水。與接下來是中對于字符串的處理。中的和在中,其類型規定了底層的數據結構,是位整數串,也即跟語言中的字符串類似。這些問題在中得到解決。 最近使用 Python 2 處理一些網絡相關的問題,被 Unicode, String 相關的一系列編碼問題搞得一頭霧水。在這里整理一下相關的概念吧。 ASCII Unicode UTF8...
摘要:在控制臺執行命令中文,可以將解釋為命令,中文,從而到到對象。中文以上的對象其實是,即字節碼,若終端是編碼的話,那么就是用的字節碼。那么這里的是什么呢默認是,這正是錯誤為什么報無法用解碼的原因中文將默認編碼改為,即可。 問題 在平時工作中,遇到了這樣的錯誤: UnicodeDecodeError: ascii codec cant decode byte 想必大家也都碰到過,很常見 。于...
摘要:關于解決亂碼問題的終極解決方案有個特別好玩的現象,當我們為了編碼頭疼的時候,幾乎搜索到所有的文章都會先發一通牢騷。另外,關于的亂碼問題,又是一個新的較長篇章。 關于解決Python亂碼問題的終極解決方案 (TL;DR) showImg(https://segmentfault.com/img/remote/1460000013229494?w=809&h=184); 有個特別好玩的現象...
摘要:所以,哪怕是初學者,都要了解并能夠解決字符編碼問題。在這個世界上,有好多不同的字符編碼。目前最新的版本為,已收入超過十萬個字符第十萬個字符在年獲采納。涵蓋的數據除了視覺上的字形編碼方法標準的字符編碼外,還包含了字符特性,如大小寫字母。 字符編碼,在編程中,是一個讓學習者比較郁悶的東西,比如一個str,如果都是英文,好說多了。但恰恰不是如此,中文是我們不得不用的。所以,哪怕是初學者,都要...
閱讀 2561·2021-11-22 09:34
閱讀 3539·2021-11-15 11:37
閱讀 2341·2021-09-13 10:37
閱讀 2105·2021-09-04 16:40
閱讀 1564·2021-09-02 15:40
閱讀 2456·2019-08-30 13:14
閱讀 3326·2019-08-29 13:42
閱讀 1903·2019-08-29 13:02