接著上節(jié)的思路說,一個(gè)網(wǎng)頁要想在瀏覽器中能夠正確顯示,需要在三個(gè)地方保持編碼的一致:網(wǎng)頁文件,網(wǎng)頁編碼聲明和瀏覽器編碼設(shè)置。
首先是網(wǎng)頁文件本身的編碼,即網(wǎng)頁文件在被創(chuàng)建的時(shí)候使用什么編碼來保存。這個(gè)完全取決于創(chuàng)建該網(wǎng)頁的人員使用了什么編碼保存,而進(jìn)一步的取決于該人員使用的操作系統(tǒng)。例如我們使用的中文版WindowsXP系統(tǒng),當(dāng)你新建一個(gè)文本文件,寫入一些內(nèi)容,并按下ctrl+s進(jìn)行保存的那一刻,操作系統(tǒng)就替你使用GBK編碼將文件進(jìn)行了保存(沒有使用UTF-8,也沒有使用UTF-16)。而使用了英文系統(tǒng)的人,系統(tǒng)會(huì)使用ISO-8859-1進(jìn)行保存,這也意味著,在英文系統(tǒng)的文件中如果輸入一個(gè)漢字,是無法進(jìn)行保存的(當(dāng)然,你甚至都無法輸入)。
一個(gè)在創(chuàng)建XML文件時(shí)(創(chuàng)建HTML的時(shí)候倒很少有人這么做)常見的誤解是以為只要在頁面的encoding部分聲明了UTF-8,則文件就會(huì)被保存為UTF-8格式。這實(shí)在是……怎么說呢,不能埋怨大家。實(shí)際上XML文件中encoding部分與HTML文件中的charset中一樣,只是告訴“別人”(這個(gè)別人可能是瀏覽你的頁面的人,可能是瀏覽器,也可能是處理你頁面的程序,別人需要知道這個(gè),因?yàn)槌悄愀嬖V他們,否則誰也猜不出你用了什么編碼,僅通過文件的內(nèi)容判斷不出使用了什么編碼,這是真的)這個(gè)文件使用了什么編碼,唯獨(dú)操作系統(tǒng)不會(huì)搭理,它仍然會(huì)按自己默認(rèn)的編碼方式保存文件(再一次的,在我們的中文WindowsXP系統(tǒng)中,使用GBK保存)。至于這個(gè)文件是不是真的是encoding或者charset所聲明的那種編碼保存的呢?答案是不一定!
例如新浪的頁面就“聲稱”他是用GB2312編碼保存的,但實(shí)際上卻是GBK,也有無數(shù)的二把刀程序員用系統(tǒng)默認(rèn)的GBK保存了他們的XML文件,卻在他們的encoding中信誓旦旦的說是UTF-8的。
這就是我們所說的第二個(gè)位置,網(wǎng)頁編碼聲明中的編碼應(yīng)該與網(wǎng)頁文件保存時(shí)使用的編碼一致。
而瀏覽器的編碼設(shè)置實(shí)際上并不嚴(yán)格,就像我們第三節(jié)所說的那樣,在瀏覽器中選擇使用GB2312來查看,它實(shí)際上仍然會(huì)使用GBK進(jìn)行。而且瀏覽器還有這樣一種好習(xí)慣,即它會(huì)盡量猜測(cè)使用什么編碼查看最合適。
我要重申的是,網(wǎng)頁文件的編碼和網(wǎng)頁文件中聲明的編碼保持一致,這是一個(gè)極好的建議(值得遵循,會(huì)與人方便,與己方便),但如果不一致,只要網(wǎng)頁文件的編碼與瀏覽器的編碼設(shè)置一致,也是可以正確顯示的。
例如有這樣一個(gè)頁面,它使用GBK保存,但聲明自己是UTF-8的。這個(gè)時(shí)候用瀏覽器打開它,首先會(huì)看到亂碼,因?yàn)檫@個(gè)頁面“告訴”瀏覽器用UTF-8顯示,瀏覽器會(huì)很尊重這個(gè)提示,于是亂碼一片。但當(dāng)手工把瀏覽器設(shè)為GBK之后,顯示正常。
說了以上四節(jié)這么多,后面我們就來侃侃Java里的字符編碼,你會(huì)發(fā)現(xiàn)有意思且撓頭的事情很多,但一旦弄通,天下無敵(不過不要像東方不敗那樣才好)。