整理這些技術筆記真的很花時間,如果你願意 關閉 Adblock 支持我,我會把這份感謝轉換成更多「踩坑轉避坑」的內容給你!ヽ(・∀・)ノ
【Day 19】從 ASCII 到 Unicode——文字編碼全面升級

從 ASCII 到 Unicode——文字編碼全面升級
有一次在網咖查資料時,我打開某個網頁,結果裡面的文字全都是亂碼,看起來就像這樣……

我已經忘了當時是在查什麼,只記得那時候用 Google 找資料,點進去某個網站後整頁全是亂碼。
「ㄟ,這網站怎麼變這樣啊?」我忍不住問了在網咖認識的朋友。
他笑了一下,說:「很簡單啦,打開瀏覽器設定,把字元編碼改成 UTF-8 就好了。」
Note
早期可以透過瀏覽器手動設定字元編碼,但現在大部分的瀏覽器都會自動偵測並設定,因此亂碼的情況已經很少見了。
「哎!變成正常了!為什麼啊?」我問。
「阿災~反正遇到亂碼就改成 UTF-8 就對了。」他說。
當下我只覺得問題能解決就好,也沒多想,哪知道隔天的資訊課,老師剛好就在講 「文字編碼」 。
文字編碼的基礎
還記得前一篇提到的 ASCII 嗎?我們說過 ASCII 是一種 「文字編碼」 ,它透過二進位對應到字母、數字和符號,讓這些內容能顯示在電腦畫面上。
不過,ASCII 早期僅支援 7 位元,也就是 2^7 = 128 個字元(代表 128 種不同符號)。這樣的限制,使得 ASCII 無法涵蓋其他語言的字元,例如中文、日文、韓文等等——畢竟它在設計之初,就是專門針對英語而來。
Note
也因為早期 ASCII 是針對英語設計的,所以後來才會改叫 「US-ASCII」 ,意指「美國標準資訊交換碼」。
為了彌補 ASCII 的不足,後來又延伸出了 「EASCII(Extended ASCII)」 。那麼,EASCII 和 ASCII 有什麼差別呢?最主要的不同點是:EASCII 擴充到 8 位元,也就是 2^8 = 256 個字元,因此能支援更多符號。
由於 EASCII 是在 ASCII 的基礎上擴充而來,所以它也具備以下特性:
- 向下相容: EASCII 的 0~127 字元與 ASCII 完全相同,這意味著所有的 ASCII 字元在 EASCII 中仍然可以使用。
- 擴充字元集: 在原本 ASCII 的基礎上,EASCII 新增了 128~255 的字元範圍,用來表示更多符號,例如歐洲語言的特殊字母、數學符號等等。
不過這裡要特別注意,EASCII 並不是一個國際統一標準,因為不同的系統或應用程式可能會使用不同的 EASCII 編碼方式,當時可說是「各自為政」,也因此常常引發「亂碼」問題。
以下提供一個 ASCII 與 EASCII 表格給參考:
| 項目 | ASCII | EASCII(Extended ASCII) |
|---|---|---|
| 全名 | American Standard Code for Information Interchange | Extended ASCII |
| 位元數(bit) | 7 bits → 128 組合 | 8 bits → 256 組合 |
| 數值範圍 | 0 ~ 127 | 0 ~ 255 |
| 是否標準定義 | 是,國際標準 | 各家自定擴充 → 沒有「全球一致標準」 |
| 高位元區(128~255) | 無定義 | 各家放特殊符號、國際字元、圖形字元 |
| 主要用途 | 基本英文、數字、標點、控制碼 | 支援歐洲語言、圖形符號、商用需求等 |
那為什麼現在我們已經不用再擔心編碼問題了呢?
是因為瀏覽器夠聰明能自己辨識?還是因為電腦硬體升級了?
其實都不是,真正的原因是後來出現了 「UNICODE(萬國碼)」 這個標準。

這裡先破個迷思:很多人(包含以前的我)都以為 Unicode 是一種字元編碼方式。
前面介紹過的 ASCII、EASCII 確實屬於字元編碼方式,但 Unicode 實際上並不是編碼方式,而是一個「字元集」。
你可以把它想像成一本「國際字典」,收錄了世界上所有文字和符號,並且為每個字元分配一個獨特的編碼,這個編碼就叫做 「碼點(Code Point)」 。
例如:
| 字元 | 碼點(Code Point) |
|---|---|
| A | U+0041 |
| B | U+0042 |
| C | U+0043 |
| 你 | U+4F60 |
| 我 | U+6211 |
| 中 | U+4E2D |
| 😀 | U+1F600 |
| 🐱 | U+1F431 |
透過這樣的設計,Unicode 能夠支援全世界的文字與符號,並有效避免亂碼問題。而從上面的表格也能看出,Unicode 的碼點都是以 U+ 開頭的十六進位數字來表示。
那麼 UNICODE 所採用的位元是多少呢?
是 21 位元,這也代表 UNICODE 比 ASCII 和 EASCII 都要大得多,因為:
- ASCII 只有 7 位元,能表示 2^7 = 128 個碼點。
- EASCII 擴充到 8 位元,能表示 2^8 = 256 個碼點。
- UNICODE 擴充到 21 位元,能表示 2^21 = 2,097,152 個碼點。
這樣的位元數已經足夠支援世界上所有的文字、符號等。
在前面我們說 UNCODE 是一個「字元集」,那麼它的編碼方式又是什麼呢?其實 UNICODE 有三種編碼方式:
- UTF-8: 又稱可變長度字元編碼,使用 1 到 4 個位元組來表示一個字元,向下相容 ASCII,適合用於網路傳輸。
- UTF-16: 使用 2 或 4 個位元組來表示一個字元,適合用於內存和檔案存儲。
- UTF-32: 使用 4 個位元組來表示一個字元,簡單但佔用空間較大。
以我們最常見使用的是 UTF-8 為例,UTF-8 的編碼方式是可變長度的,什麼是可變長度呢?
簡單來講,每個字元所佔用的位元組會隨著字元的複雜度而有所不同
- 對於 ASCII 字元(0~127) ,剛好對應 U+0000 到 U+007F,使用 1 個位元組表示。
- 對於 U+0080 ~ U+07FF 的字元 ,使用 2 個位元組表示(這是屬於歐系語言的字元)。
- 對於 U+0800 ~ U+FFFF 的字元 ,使用 3 個位元組表示(這是屬於中日韓、數學符號的區間)。
- 對於 U+10000 ~ U+10FFFF 的字元 ,使用 4 個位元組表示(這是屬於表情符號、特殊符號或是生僻字元的區間)。
這也是為什麼前面表格你會看到 A 的編碼是 U+0041,而 😀 的編碼是 U+1F600 的原因。
最後,我們也來聊聊 UTF-8 常用的進位方式- 「十六進位(Hexadecimal)」 。
簡單來說,十六進位就是十進位的延伸。我們知道十進位用 09 表示數字,超過 9 就進位。9 之外,還加入了 A
而在十六進位中,除了 0F 這六個字母來表示 1015。
所以表示方式如下:
1 | |
關於 UTF-8,你只要先掌握幾個重點就好,其他細節有需要再去查就行:
- UTF-8 是一種可變長度的編碼方式 ,隨著字元的複雜度而有所不同。
- UTF-8 向下相容 ASCII ,也就是說,所有的 ASCII 字元在 UTF-8 中仍然可以使用。
- 十六進位是 UTF-8 的表示方式 ,這樣可以更方便地表示字元的編碼。
- UNICODE 是一個字元集 ,它收錄了世界上所有的文字、符號等,並且不會有亂碼的問題。
以上就是關於 UNICODE 的基礎介紹,這樣的編碼方式讓我們可以在網路上自由地使用各種文字、符號,而不必擔心亂碼的問題囉~
當然,你也可以寫程式來查詢 UNICODE 的碼點,這邊我就以 JavaScript 為例:
1 | |
See the Pen UNICODE UTF-8 by Ray (@hsiangfeng) on CodePen.
這段程式碼會在你按下鍵盤時,顯示「按下的鍵」以及對應的 Unicode 碼點:
結語
這裡先提醒一下讀者,因為接下來的章節會開始介紹一些程式碼與工程相關的知識,過程中可能會需要用到開發者環境,例如:
當然,你也可以選擇不安裝這些工具,單純閱讀內容也完全沒問題,只是會少了一些實作體驗。
如果你有興趣,還是建議把工具安裝起來,這樣會更有感覺。
另外也不用擔心,後面的章節並不會深入鑽研程式碼,而是以基本概念為主,輕鬆帶過就好~
同步更新
本文將同步更新至以下網站:
整理這些技術筆記真的很花時間,如果你願意 關閉 Adblock 支持我,我會把這份感謝轉換成更多「踩坑轉避坑」的內容給你!ヽ(・∀・)ノ