張北一
網(wǎng)頁設(shè)計(jì)與制作是北京市現(xiàn)行信息技術(shù)教材信息技術(shù)基礎(chǔ)中的重要內(nèi)容。教師在備課時(shí)通過研讀教材可以發(fā)現(xiàn),網(wǎng)頁是加工和表達(dá)信息的一種強(qiáng)大載體,基本網(wǎng)頁制作技術(shù)也是高中生應(yīng)會的基本技能。
教材第四單元第三節(jié)指出,網(wǎng)頁是使用HTML語言編寫的純文本文件。瀏覽器根據(jù)文件中所寫的標(biāo)簽來進(jìn)行顯示并賦予不同文本不同的樣式。所以理論上,所有文本編輯軟件皆可用來編寫網(wǎng)頁。例如,Windows記事本、Sublime Text、GNU Nano都可以勝任網(wǎng)頁編輯工作。在教學(xué)實(shí)踐中,常有學(xué)生使用Windows系統(tǒng)自帶的記事本軟件編寫和修改.html文件,此時(shí)就可能會有學(xué)生遇到“記事本”編寫的中文頁面在瀏覽器中亂碼的問題,具體情況我們可以用一組實(shí)驗(yàn)來說明。
實(shí)驗(yàn)過程
我們使用微軟Windows7 64位簡體中文操作系統(tǒng)和internet explorer 11進(jìn)行測試。測試步驟如下。
1.打開記事本軟件,輸入.html文檔中必要的html、head、body標(biāo)簽。并在body標(biāo)簽下輸入文本“This is a test.這是一個(gè)測試”。寫法上頁如上頁圖1所示。
2.將文件按默認(rèn)配置保存為index.html。
3.打開internet explorer,將index.html拖拽到瀏覽器窗口中。發(fā)現(xiàn)英文字符顯示正常,但中文顯示為亂碼(如圖2)。
4.查閱網(wǎng)上資料后,可得知通過調(diào)節(jié)瀏覽器“編碼”選項(xiàng)可以解決這一問題。我們在瀏覽器窗口內(nèi)點(diǎn)擊鼠標(biāo)右鍵,在“編碼”一項(xiàng)中勾選“自動選擇”(如圖3)。此后發(fā)現(xiàn)中文字符顯示正常。
5.取消自動選擇選項(xiàng),嘗試手動選擇編碼方式為“簡體中文(GB2312)”或“Unicode(UTF-8)”。發(fā)現(xiàn)選擇“簡體中文(GB2312)”時(shí)中文字符正常顯示;選擇“Unicode(UTF-8)”時(shí)中文字符亂碼。
6.確定了中文顯示問題是由編碼方式引起的,那么回到記事本軟件并打開index.html,重新檢查保存文件時(shí)的選項(xiàng),發(fā)現(xiàn)也有“編碼”一項(xiàng)。其默認(rèn)值為“ANSI”。我們將其調(diào)節(jié)為瀏覽器編碼選項(xiàng)中出現(xiàn)過的“UTF-8”并重新使用瀏覽器打開index.html后發(fā)現(xiàn)中文字符正常顯示。
7.保持index.html的編碼方式為UTF-8不變,使用瀏覽器打開并設(shè)置瀏覽器編碼方式為“簡體中文(GB2312)”,發(fā)現(xiàn)中文顯示亂碼。
8.繼續(xù)對其他語種文字進(jìn)行驗(yàn)證。我們先加上一行日語(如圖4)。分別以ANSI、Unicode、UTF-8來保存文件,并使用瀏覽器以GB2312、Unicode和日語(EUC)來瀏覽這個(gè)文件。結(jié)果如表1所示。
9.再增加一行法語字符,這里面特別注意要包含法語中特有的字母“”,重復(fù)第八步的實(shí)驗(yàn)。從中我們發(fā)現(xiàn)保存為ANSI編碼文件的時(shí)候系統(tǒng)提示無法保存該文件(如下頁圖5)。所以只存為Unicode和UTF-8兩種格式。結(jié)果如下頁表2。
由上面的實(shí)驗(yàn)我們可以得知,當(dāng)保存文件所選的編碼和瀏覽器設(shè)置的編碼器一致時(shí),各種字符皆顯示正常。不一致時(shí),部分字符會出現(xiàn)亂碼。為了避免用戶頻繁切換編碼方式,瀏覽器開發(fā)者均設(shè)置了“自動選擇”選項(xiàng)來幫助用戶自動切換編碼方式。但實(shí)驗(yàn)中還引發(fā)了三個(gè)問題:①為什么保存文件和瀏覽文件時(shí)必須選擇一致的編碼方式才能保證文件的正常顯示?②實(shí)驗(yàn)證實(shí)ANSI和GB2312應(yīng)屬同一種編碼方式,但為何名稱不同?二者又有什么關(guān)系?③在瀏覽器設(shè)置中Unicode被寫作“Unicode(UTF-8)”,但記事本軟件的保存選項(xiàng)卻將“Unicode”和“UTF-8”列為不同的選項(xiàng),這兩者又是什么關(guān)系?
下面我們就來針對這三個(gè)問題逐一討論。
文字在計(jì)算機(jī)內(nèi)的表達(dá)
我們知道計(jì)算機(jī)內(nèi)部存儲信息是靠“0”和“1”這兩個(gè)二進(jìn)制數(shù)實(shí)現(xiàn)的。如果想表達(dá)其他的文字和符號,就要想一個(gè)辦法用“0”和“1”來進(jìn)行指代。最早的ASCII碼就是使用八位(1字節(jié))二進(jìn)制數(shù)來指代數(shù)字、小寫英語字母、大寫英語字母和常用符號的規(guī)則。其中首位統(tǒng)一規(guī)定為0,此后的7位來表示不同的符號。表3為a、b、c三個(gè)小寫英文字母與其二進(jìn)制編碼的對應(yīng)關(guān)系。
這種把字符轉(zhuǎn)換為二進(jìn)制數(shù)在計(jì)算機(jī)內(nèi)存儲的做法即為“編碼”。ASCII僅能滿足英語語言中文字的表達(dá),應(yīng)用范圍十分有限。為了方便世界各國文字和符號都能利用計(jì)算機(jī)進(jìn)行存儲和傳輸,國際標(biāo)準(zhǔn)化組織和各國的標(biāo)準(zhǔn)化結(jié)構(gòu)都編制了各種文字編碼方式,我們在實(shí)驗(yàn)中看到的GB2312、Unicode都是常用的編碼方式。每種編碼方式都自成一體地規(guī)定了文字和二進(jìn)制數(shù)之間的對應(yīng)關(guān)系。多數(shù)情況下,不同編碼方式的“文字—二進(jìn)制數(shù)”對應(yīng)關(guān)系是不同的。我們在記事本軟件中保存文件就是把文字轉(zhuǎn)換為二進(jìn)制數(shù)的過程,用瀏覽器瀏覽文件就是把二進(jìn)制數(shù)翻譯為文字的過程。如果這兩個(gè)過程的標(biāo)準(zhǔn)不一致,必然會出現(xiàn)千奇百怪的混亂符號,也就是亂碼。例如,GB2312中的漢字“中”十六進(jìn)制編碼為“D6D0”,轉(zhuǎn)換為二進(jìn)制為“11010110 11010000”。如果用另一種編碼方式Unicode來翻譯這組二進(jìn)制數(shù),則對應(yīng)字符“”,明顯和原文不符。這里要注意的是,目前多數(shù)編碼方式對英語字母的二進(jìn)制表達(dá)都是一致的,所以在實(shí)驗(yàn)第八步中英語字母總能正常顯示。
漢字編碼在編程中應(yīng)用十分廣泛。例如,Arduino單片機(jī)支持一種朗讀中文的語音合成模塊。在源代碼中會以十六進(jìn)制數(shù)組成的數(shù)組來確定發(fā)音內(nèi)容。使用說明中會寫清模塊支持的編碼方式,以便開發(fā)者查閱漢字和其十六進(jìn)制數(shù)的對應(yīng)關(guān)系。如果代碼中寫道uint8_t text[]={0xB3,0xC9},其中B3C9在gb2312中就是“成”字。模塊在工作時(shí)就會發(fā)出“成”字的讀音。除了語音模塊,在對液晶顯示模塊時(shí)也需要依靠十六進(jìn)制數(shù)來指代漢字。
文字編碼在網(wǎng)絡(luò)傳輸中同樣普遍存在。我們在瀏覽中文維基百科時(shí),瀏覽器地址欄中會顯示形如“https://zh.wikipedia.org/wiki/中國”的地址,而將網(wǎng)址復(fù)制到文本編輯器中就會發(fā)現(xiàn)其中的“中國”變成了“%E4%B8%AD%E5%9C%8B”。這就是因?yàn)樵趥鬏數(shù)臅r(shí)候“中國”被使用UTF-8編碼成了十六進(jìn)制數(shù)添加到網(wǎng)址中,而瀏覽器在收到網(wǎng)址后又將其解碼成了漢字并在地址欄顯示出來。
ANSI與GB2312編碼
理解了“編碼”的含義后,我們就明白了記事本軟件和瀏覽器中“編碼”選項(xiàng)的作用了。那么記事本軟件中默認(rèn)的“ANSI”又是一種什么編碼方式呢?實(shí)際上ANSI在不同語言的操作系統(tǒng)上指代的編碼方式是不一樣的。當(dāng)我們選擇編碼為“ANSI”時(shí),系統(tǒng)會從一種被稱為“Code Page”(代碼頁)的編碼標(biāo)準(zhǔn)中集中選取與當(dāng)前操作系統(tǒng)語言和區(qū)域設(shè)置相符的編碼標(biāo)準(zhǔn)。在微軟MSDN網(wǎng)站的Code Page Identifiers文檔中明確記載簡體中文操作系統(tǒng)應(yīng)選的Code Page標(biāo)識符為“936”,名稱為“gb2312”,附加信息中解釋為“ANSI/OEM Simplified Chinese (PRC, Singapore); Chinese Simplified (GB2312)”。說明系統(tǒng)為中國和新加坡的中文用戶選擇GB2312為指定編碼方式。而GB2312是中國國家標(biāo)準(zhǔn)總局所頒布的《信息交換用漢字字符集》,也就是我國所統(tǒng)一規(guī)定的漢字編碼依據(jù)。其中規(guī)定了包含英語字母、中文漢字、日語假名、希臘字母等7445個(gè)符號。這就是為什么選擇以ANSI保存文件后應(yīng)該將瀏覽器“編碼”選項(xiàng)設(shè)置為“簡體中文(GB2312)”才能正常閱讀漢字和日文的原因。
ANSI Code Page是Windows操作系統(tǒng)獨(dú)有的編碼方式集合,其包含了很多種適用于各國語言的編碼方式。在Windows中,用戶也可以自己決定系統(tǒng)選擇何種編碼方式來解碼應(yīng)用程序中的文字符號。我們可以在“控制面板→區(qū)域→管理→更改系統(tǒng)區(qū)域設(shè)置”這一選項(xiàng)中選擇。中國大陸一般會選擇為“中文(簡體,中國)”。如果經(jīng)常運(yùn)行繁體中文軟件,則可以選擇為“中文(繁體,香港特別行政區(qū))”等。
有一些Windows軟件可能不會在編碼方式選項(xiàng)中直接提供“ANSI”選項(xiàng),但會提供含有Code Page標(biāo)識符的選項(xiàng),讓用戶不受系統(tǒng)自動選擇編碼方式的限制。在我們常用的SSH工具“Putty”中,其“Translation”選項(xiàng)中就提供了形如“Win 1250”“Win 1256”等選項(xiàng)。其中“1250”“1256”就是Code Page標(biāo)識符,分別代表了中歐和阿拉伯。
Unicode編碼
GB2312雖然能解決大部分的我國常用文字符號的編碼問題,但其中仍然沒有包含法語等其他國家的字符。那么有沒有一種編碼方式能解決各國所有文字的編碼問題呢?答案是肯定的,那就是實(shí)驗(yàn)第九步中系統(tǒng)向我們提示的“Unicode”。Unicode是由Unicode協(xié)會定制、發(fā)布的一種針對各國文字、符號進(jìn)行編碼的編碼方式。所以Unicode又被稱為“萬國碼”。Unicode誕生時(shí)規(guī)定用16位二進(jìn)制數(shù)來表示一個(gè)文字或符號。但最早的Unicode和ASCII有一定差異,導(dǎo)致原本處理ASCII的程序沒法直接處理Unicode編碼的文字。于是Unicode協(xié)會又制定了一種Unicode的變種編碼方式,稱為UTF-8。UTF-8中,理論上最多能用48位二進(jìn)制數(shù)(6字節(jié))來表示一個(gè)文字或符號。對于單字節(jié)符號,UTF-8與ASCII一致,使得原本處理ASCII的軟件幾乎不用做專門的修改就能處理UTF-8與ASCII的交集中的文字和符號。表示ASCII以外的文字時(shí),則在前8位中加入說明本字符共需要多少位的信息。我們在記事本軟件中看到的“Unicode”選項(xiàng)的含義是每個(gè)字符占用16位的標(biāo)準(zhǔn)Unicode編碼方式;“UTF-8”專指Unicode的變種UTF-8。當(dāng)我們選擇瀏覽器選項(xiàng)中的“Unicode(UTF-8)”時(shí),瀏覽器會自動判斷使用標(biāo)準(zhǔn)Unicode或者UTF-8。
在使用計(jì)算機(jī)處理非ASCII符號時(shí)要謹(jǐn)慎選擇其編碼方式。通用性良好的編碼方式能使用戶所編碼的信息在各種環(huán)境下都能被輕松解碼。例如,信息技術(shù)基礎(chǔ)第三單元第二節(jié)中介紹了使用數(shù)據(jù)庫存儲信息。我們在MySQL等數(shù)據(jù)庫管理系統(tǒng)中建立數(shù)據(jù)庫時(shí),編碼方式就是一個(gè)重要的選項(xiàng)。選擇UTF-8等包含字符量大、通用性強(qiáng)的編碼方式會有助于各種應(yīng)用程序(如PHP腳本程序)被順利讀取和解碼數(shù)據(jù)庫中的文字信息。也有利于正確地存儲用戶所提交的小語種文字、生僻字等文字符號。
以上就是對計(jì)算機(jī)文字編碼的簡要介紹。文字編碼是信息技術(shù)中的基礎(chǔ)知識。本文介紹的文字對十六進(jìn)制數(shù)或二進(jìn)制數(shù)代碼轉(zhuǎn)換標(biāo)準(zhǔn)是公開的。如果使用一種不公開的轉(zhuǎn)換標(biāo)準(zhǔn),就可以實(shí)現(xiàn)對文字的加密,由此則可以延伸討論更多的話題。