天天看點

UTF-8 BOM頭

BOM是什麼

Unicode的學名是"Universal Multiple-Octet Coded Character Set",簡稱為UCS。UCS可以看作是"Unicode Character Set"的縮寫。在UCS 編碼中有一個叫做 "Zero Width No-Break Space",中文譯名作“零寬無間斷間隔”的字元,它的編碼是 FEFF。而 FFFE 在 UCS 中是不存在的字元,是以不應該出現在實際傳輸中。UCS 規範建議我們在傳輸位元組流前,先傳輸字元 "Zero Width No-Break Space"。這樣如果接收者收到 FEFF,就表明這個位元組流是 Big-Endian 的;如果收到FFFE,就表明這個位元組流是 Little- Endian 的。是以字元 "Zero Width No-Break Space" (“零寬無間斷間隔”)又被稱作 BOM(即Byte Order Mark)。

UTF-8 BOM頭又是什麼

UTF-8以位元組為編碼單元是以不需要 BOM 來表明位元組順序,但可以用 BOM 來表明編碼方式。字元 "Zero Width No-Break Space" 的 UTF-8 編碼是 EF BB BF。是以如果接收者收到以 EF BB BF 開頭的位元組流,就知道這是 UTF-8編碼了。

UTF-8 BOM頭

是以UTF-8編碼的字元串開頭處的三個bytes 0xef,0xbb,0xbf就稱為UTF-8 BOM頭。

為什麼excel打開沒有BOM頭的csv檔案會亂碼?

類似WINDOWS自帶的記事本等軟體,在儲存一個以UTF-8編碼的檔案時,會在檔案開始的地方插入UTF-8 BOM頭。記事本等編輯器通過它來識别這個檔案是否以UTF-8編碼(當然即便沒有UTF-8 BOM頭記事本也能通過其它方式正确識别UTF-8編碼)。

那麼如果一個UTF-8編碼的字元串的開頭處沒有BOM頭又會發生什麼?

比如我們用C#建立一個csv檔案,裡面儲存中文,日文等多國語言的字元串然後以UTF-8編碼儲存(此時沒有UTF-8 BOM頭)。

記事本能夠識别,但是excel卻識别出錯:

UTF-8 BOM頭

這是一個已知的問題,Excel打開沒有BOM頭的csv檔案時就是會這樣!

解決的辦法也很簡單,在生成字元串時手動把UTF-8 BOM頭添加在字元串的開頭處,下面是C#代碼:

sb.Append('\uFEFF');

好了,重新用Excel打開,已經可以正确識别了!

作者:sparkdev

出處:http://www.cnblogs.com/sparkdev/

本文版權歸作者和部落格園共有,歡迎轉載,但未經作者同意必須保留此段聲明,且在文章頁面明顯位置給出原文連接配接,否則保留追究法律責任的權利。

繼續閱讀