UTF-8的BOM含義- 碼上快樂
文章推薦指數: 80 %
其實很多現代腳本語言,比如Python,其解釋器本身都是能處理BOM的,但是shell卡在這里,沒辦法,只能躺着也中槍。
說起來這也不能怪shell,因為BOM本身違反 ...
碼上快樂
首頁
榜單
標簽
關於
搜索
相關內容
簡體
繁體
UTF-8的BOM含義
本文轉載自
kris_zhang
查看原文
2017-03-3011:25
12039
BOM/
UTF-8
BOM的介紹
在github上寫md文件的時候,發現生成自己blog時,報出一個錯誤是讓使用UTF-8編碼,然后在Notepad++上把文件轉成UTF-8時,發現菜單中有"UTF-8無BOM編碼格式"。
上網查了一下BOM的定義:byteordermark這個是為UTF-16和UTF-32准備的,用於標記字節序(byteorder)。
「UTF-8」和「帶BOM的UTF-8」的區別就是有沒有BOM。
即文件開頭有沒有U+FEFF。
BOM的愛恨情仇
知乎上有個比較好的文章,講了BOM問題,下面直接引用了原文:
作者:陳甫鵃鏈接:https://www.zhihu.com/question/20167122/answer/14199022來源:知乎著作權歸作者所有。
商業轉載請聯系作者獲得授權,非商業轉載請注明出處。
首先,BOM是啥。
這個就不解釋了,Wikipedia上很詳細。
http://en.wikipedia.org/wiki/Byte_order_mark。
在網頁上使用BOM是個錯誤。
BOM設計出來不是用來支持HTML和XML的。
要識別文本編碼,HTML有charset屬性,XML有encoding屬性,沒必要拉BOM撐場面。
雖然理論上BOM可以用來識別UTF-16編碼的HTML頁面,但實際工程上很少有人這么干。
畢竟UTF-16這種編碼連ASCII都雙字節,實在不適用於做網頁。
其實說BOM是個壞習慣也不盡然。
BOM也是Unicode標准的一部分,有它特定的適用范圍。
通常BOM是用來標示Unicode純文本字節流的,用來提供一種方便的方法讓文本處理程序識別讀入的.txt文件是哪個Unicode編碼(UTF-8,UTF-16BE,UTF-16LE)。
Windows相對對BOM處理比較好,是因為Windows把Unicode識別代碼集成進了API里,主要是CreateFile()。
打開文本文件時它會自動識別並剔除BOM。
Windows用這個有歷史原因,因為它最初脫胎於多代碼頁的環境。
而引入Unicode時Windows的設計者又希望能在用戶不注意的情況下同時兼容Unicode和非Unicode(Multiplebyte)文本文件,就只能借助這種小trick了。
相比之下,Linux這樣的系統在多locale的環境中浸染的時間比較短,再加上社區本身也有足夠的動力輕裝前進(吐槽:微軟對兼容性的要求確實是到了非常偏執的地步,任何一點破壞兼容性的做法都不允許,以至於很多時候是自己綁住自己的雙手),所以干脆一步到位進入UTF-8。
當然中間其實有一段過渡期,比如從最初全UTF-8的GTK+2.0發布到基本上所有GTK開發者都棄用多locale的GTK+1.2,我印象中至少經歷了三到四年。
BOM不受歡迎主要是在UNIX環境下,因為很多UNIX程序不鳥BOM。
主要問題出在UNIX那個所有腳本語言通行的首行#!標示,這東西依賴於shell解析,而很多shell出於兼容的考慮不檢測BOM,所以加進BOM時shell會把它解釋為某個普通字符輸入導致破壞#!標示,這就麻煩了。
其實很多現代腳本語言,比如Python,其解釋器本身都是能處理BOM的,但是shell卡在這里,沒辦法,只能躺着也中槍。
說起來這也不能怪shell,因為BOM本身違反了一個UNIX設計的常見原則,就是文檔中存在的數據必須可見。
BOM不能作為可見字符被文本編輯器編輯,就這一條很多UNIX開發者就不滿意。
順便說一句,即使腳本語言能處理BOM,隨處使用BOM也不是推薦的辦法。
各個腳本語言對Unicode的處理都有自己的一套,Python的#--coding:utf-8--,Perl的useutf8,都比BOM簡單而且可靠。
另一個好消息是,即使是必須在Windows和UNIX之間切換的朋友也不會悲催。
幸虧在UNIX環境下我們還有VIM這種神器,即使遇到BOM擋道,我們也可以通過setnobomb;setfileencoding=utf8;w三條命令解決問題。
最后回頭想想,似乎也真就只有Windows堅持用BOM了。
P.S.:本問題是自己的第150個回答。
突然發現自己回答得很少很少⋯⋯P.S.2:突然想起需要解釋一下為什么說VIM去除bomb的操作需要在UNIX下完成。
因為VIM在Windows環境下有一個奇怪的bug,總是把UTF-16文件識別成二進制文件,而UNIX(Linux或者Mac都可以)下VIM則無問題。
這個問題從VIM6.8一直跟着我到VIM7.3。
目前尚不清楚這是VIM的bug還是我自己那個.vimrc文件的bug。
如有高手解答不勝感激。
@引用結束
總結
以下是一些經典語錄:
HTML有charset屬性,XML有encoding屬性,沒必要拉BOM撐場面
UTF-16這種編碼連ASCII都雙字節,實在不適用於做網頁
通常BOM是用來標示Unicode純文本字節流的,讓文本處理程序識別txt文件是哪個Unicode編碼(UTF-8,UTF-16BE,UTF-16LE)
Windows相對對BOM處理比較好,打開文本文件時它會自動識別並剔除BOM.
Windows的設計者希望能在用戶不注意的情況下同時兼容Unicode和非Unicode(Multiplebyte)文本文件.
Linux一步到位進入UTF-8,過渡期至少經歷了三到四年.
BOM不受歡迎主要是在UNIX環境下,因為很多UNIX程序不鳥BOM。
因為BOM本身違反了一個UNIX設計的常見原則,就是文檔中存在的數據必須可見。
UNIX環境下我們還有VIM這種神器,即使遇到BOM擋道,我們也可以通過setnobomb;setfileencoding=utf8;w三條命令解決問題。
似乎也真就只有Windows堅持用BOM了。
UTF-8不需要BOM,所以不含BOM的UTF-8才是標准形式.
微軟在UTF-8中使用BOM是因為這樣可以把UTF-8和ASCII等編碼明確區分開
UTF-8的網頁代碼不應使用BOM,否則常常會出錯
寫C++代碼建議程序要在windows和mac還有linux上運行的話,源代碼最好保存成utf-8帶bom的格式,這樣比較通用一些。
而用utf-16無論大端還是小端,g++都不認的。
或者用utf-8不帶bom格式,然后代碼不要出現非ascii127以后的字符。
帶用bom的utf-8也是符合國際標准的
微軟在堅持使用bom上沒有錯,因為這是在為用戶考慮的。
也許給我們這些寫程序的帶來了不便,但是,計算機最廣泛的用戶不是程序員。
帶頭的鵝和去頭的鵝,有些編輯器比較傻會把去頭的鵝認成鴨子
以UTF-8格式編碼,從notepad++-->Mongodb里面復制東西的時候,莫名其妙多了不少的字節數。
如果不安裝notepad++,使用默認的記事本,那就更是個坑,默認有bom,你還無法選擇。
就是因為這個bom,CSV導入mongodb時,第一個字段總是不正常,直接導致用第一個字段作為條件find時,出不了結果!
utf8對ascii的兼容確實是它的好,但是這個優點在某些時候恰恰成了隱藏問題的缺點。
因此bom大法好,加bom保平安.
為什么windows的記事本要強行給utf8加bom的原因——為了兼容舊系統的編碼問題,unix陣營放棄帶bom的utf8——為了讓它們的上古程序能繼續運行下去,這個各自有自己利益訴求的差異決定其實並不對錯
參考:
https://www.zhihu.com/question/20167122
http://jimliu.net/2015/03/07/something-about-encoding-extra/
×
免責聲明!
本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。
如果侵犯了您的隱私權益,請聯系本站郵箱[email protected]刪除。
猜您在找
UTF-8BOM頭
UTF-8與UTF-8(BOM)區別
UTF-8與UTF-8(BOM)區別
UTF-8帶BOM和不帶BOM的轉換
UTF-8和UTF—8Bom的區別(轉)
UTF-8(withBOM)與UTF-8相互轉換
【改】utf-8的去掉BOM的方法
UTF-8BOM(EFBBBF)
utf-8無bom格式編碼
python帶BOM頭utf-8的響應解碼
粵ICP備18138465號
©2018-2022CODEPRJ.COM
延伸文章資訊
- 1到底什麼是UTF-8 BOM頭- 壹讀
- 2這些是什麼? BOM/UFT-8有簽章/withBOM/withoutBOM - iT 邦幫忙
這是另一篇關於BOM之亂的描述. Windows 作業系統不少程式(像是記事本),預設會對UTF-8 檔案加上BOM 而Linux 則避免妨礙到像是解譯器腳本而不加BOM,對於沒有預期要 ...
- 3「帶BOM 的UTF-8」和「無BOM 的UTF-8」有什麼區別?網頁 ...
受邀。早知道上得山多終遇老虎,在@梁海老兄面前耍Unicode總會有這一天的??首先,BOM是啥。這個就不解釋了,Wikipedia上很 ...
- 4utf-8無BOM編碼格式什麼意思? - 程式人生
UTF-8不需要BOM來表明位元組順序,但可以用BOM來表明編碼方式。字元"ZERO WIDTH NO-BREAK SPACE"的UTF-8編碼是EF BB BF。所以如果接收者收到以EF BB...
- 5UTF-8 BOM (Byte Order Mark) 的問題@新精讚
在Michael Kaplan 那看到Every character has a story #4: U+feff (alternate title: UTF-8 is the BOM, dud...