學習JavaIO的時候遇到編碼,感覺一臉蒙B,於是研究了一下編碼這個東西,以下是個人的總結,有不足之處請多多指正。
我們都知道計算機存儲的最小單位是字節,而一個字節是八位,也就是說一個字節能表示的範圍是0~255,由於一開始計算機誕生於美國,所以美國人首先在上面對英語進行編碼,就出現了ASCII編碼,表示了0~127,剩下的128~255便空着,後來,很多的其他語言都在128~255上面進行制定自己的編碼,我們國家由於漢字較多,常用漢字就有6000多個,要是按照一個字節編碼,根本不夠用,所以就有人想出了兩個字節編碼一個字,0~127仍然按照原來的編碼(一個字節編碼方式)這就出現了全角與半角。下面附上一張0~127的ASCII表:
Bin
|
Oct |
Dec
|
Hex
|
縮寫/字符
|
解釋
|
0000 0000
|
0
|
0
|
00
|
NUL(null)
|
空字符
|
0000 0001
|
1
|
1
|
01
|
SOH(start of headline)
|
標題開始
|
0000 0010
|
2
|
2
|
02
|
STX (start of text)
|
正文開始
|
0000 0011
|
3
|
3
|
03
|
ETX (end of text)
|
正文結束
|
0000 0100
|
4
|
4
|
04
|
EOT (end of transmission)
|
傳輸結束
|
0000 0101
|
5
|
5
|
05
|
ENQ (enquiry)
|
請求
|
0000 0110
|
6
|
6
|
06
|
ACK (acknowledge)
|
收到通知
|
0000 0111
|
7
|
7
|
07
|
BEL (bell)
|
響鈴
|
0000 1000
|
10
|
8
|
08
|
BS (backspace)
|
退格
|
0000 1001
|
11
|
9
|
09
|
HT (horizontal tab)
|
水平製表符
|
0000 1010
|
12
|
10
|
0A
|
LF (NL line feed, new line)
|
換行鍵
|
0000 1011
|
13
|
11
|
0B
|
VT (vertical tab)
|
垂直製表符
|
0000 1100
|
14
|
12
|
0C
|
FF (NP form feed, new page)
|
換頁鍵
|
0000 1101
|
15
|
13
|
0D
|
CR (carriage return)
|
回車鍵
|
0000 1110
|
16
|
14
|
0E
|
SO (shift out)
|
不用切換
|
0000 1111
|
17
|
15
|
0F
|
SI (shift in)
|
啓用切換
|
0001 0000
|
20
|
16
|
10
|
DLE (data link escape)
|
數據鏈路轉義
|
0001 0001
|
21
|
17
|
11
|
DC1 (device control 1)
|
設備控制1
|
0001 0010
|
22
|
18
|
12
|
DC2 (device control 2)
|
設備控制2
|
0001 0011
|
23
|
19
|
13
|
DC3 (device control 3)
|
設備控制3
|
0001 0100
|
24
|
20
|
14
|
DC4 (device control 4)
|
設備控制4
|
0001 0101
|
25
|
21
|
15
|
NAK (negative acknowledge)
|
拒絕接收
|
0001 0110
|
26
|
22
|
16
|
SYN (synchronous idle)
|
同步空閒
|
0001 0111
|
27
|
23
|
17
|
ETB (end of trans. block)
|
結束傳輸塊
|
0001 1000
|
30
|
24
|
18
|
CAN (cancel)
|
取消
|
0001 1001
|
31
|
25
|
19
|
EM (end of medium)
|
媒介結束
|
0001 1010
|
32
|
26
|
1A
|
SUB (substitute)
|
代替
|
0001 1011
|
33
|
27
|
1B
|
ESC (escape)
|
換碼(溢出)
|
0001 1100
|
34
|
28
|
1C
|
FS (file separator)
|
文件分隔符
|
0001 1101
|
35
|
29
|
1D
|
GS (group separator)
|
分組符
|
0001 1110
|
36
|
30
|
1E
|
RS (record separator)
|
記錄分隔符
|
0001 1111
|
37
|
31
|
1F
|
US (unit separator)
|
單元分隔符
|
0010 0000
|
40
|
32
|
20
|
(space)
|
空格
|
0010 0001
|
41
|
33
|
21
|
!
|
歎號 |
0010 0010
|
42
|
34
|
22
|
"
|
雙引號 |
0010 0011
|
43
|
35
|
23
|
#
|
井號 |
0010 0100
|
44
|
36
|
24
|
$
|
美元符 |
0010 0101
|
45
|
37
|
25
|
%
|
百分號 |
0010 0110
|
46
|
38
|
26
|
&
|
和號 |
0010 0111
|
47
|
39
|
27
|
'
|
閉單引號 |
0010 1000
|
50
|
40
|
28
|
(
|
開括號
|
0010 1001
|
51
|
41
|
29
|
)
|
閉括號
|
0010 1010
|
52
|
42
|
2A
|
*
|
星號 |
0010 1011
|
53
|
43
|
2B
|
+
|
加號 |
0010 1100
|
54
|
44
|
2C
|
,
|
逗號 |
0010 1101
|
55
|
45
|
2D
|
-
|
減號/破折號 |
0010 1110
|
56
|
46
|
2E
|
.
|
句號 |
00101111
|
57
|
47
|
2F
|
/
|
斜槓 |
00110000
|
60
|
48
|
30
|
0
|
數字0 |
00110001
|
61
|
49
|
31
|
1
|
數字1 |
00110010
|
62
|
50
|
32
|
2
|
數字2 |
00110011
|
63
|
51
|
33
|
3
|
數字3 |
00110100
|
64
|
52
|
34
|
4
|
數字4 |
00110101
|
65
|
53
|
35
|
5
|
數字5 |
00110110
|
66
|
54
|
36
|
6
|
數字6 |
00110111
|
67
|
55
|
37
|
7
|
數字7 |
00111000
|
70
|
56
|
38
|
8
|
數字8 |
00111001
|
71
|
57
|
39
|
9
|
數字9 |
00111010
|
72
|
58
|
3A
|
:
|
冒號 |
00111011
|
73
|
59
|
3B
|
;
|
分號 |
00111100
|
74
|
60
|
3C
|
<
|
小於 |
00111101
|
75
|
61
|
3D
|
=
|
等號 |
00111110
|
76
|
62
|
3E
|
>
|
大於 |
00111111
|
77
|
63
|
3F
|
?
|
問號 |
01000000
|
100
|
64
|
40
|
@
|
電子郵件符號 |
01000001
|
101
|
65
|
41
|
A
|
大寫字母A |
01000010
|
102
|
66
|
42
|
B
|
大寫字母B |
01000011
|
103
|
67
|
43
|
C
|
大寫字母C |
01000100
|
104
|
68
|
44
|
D
|
大寫字母D |
01000101
|
105
|
69
|
45
|
E
|
大寫字母E |
01000110
|
106
|
70
|
46
|
F
|
大寫字母F |
01000111
|
107
|
71
|
47
|
G
|
大寫字母G |
01001000
|
110
|
72
|
48
|
H
|
大寫字母H |
01001001
|
111
|
73
|
49
|
I
|
大寫字母I |
01001010
|
112
|
74
|
4A
|
J
|
大寫字母J |
01001011
|
113
|
75
|
4B
|
K
|
大寫字母K |
01001100
|
114
|
76
|
4C
|
L
|
大寫字母L |
01001101
|
115
|
77
|
4D
|
M
|
大寫字母M |
01001110
|
116
|
78
|
4E
|
N
|
大寫字母N |
01001111
|
117
|
79
|
4F
|
O
|
大寫字母O |
01010000
|
120
|
80
|
50
|
P
|
大寫字母P |
01010001
|
121
|
81
|
51
|
Q
|
大寫字母Q |
01010010
|
122
|
82
|
52
|
R
|
大寫字母R |
01010011
|
123
|
83
|
53
|
S
|
大寫字母S |
01010100
|
124
|
84
|
54
|
T
|
大寫字母T |
01010101
|
125
|
85
|
55
|
U
|
大寫字母U |
01010110
|
126
|
86
|
56
|
V
|
大寫字母V |
01010111
|
127
|
87
|
57
|
W
|
大寫字母W |
01011000
|
130
|
88
|
58
|
X
|
大寫字母X |
01011001
|
131
|
89
|
59
|
Y
|
大寫字母Y |
01011010
|
132
|
90
|
5A
|
Z
|
大寫字母Z |
01011011
|
133
|
91
|
5B
|
[
|
開方括號 |
01011100
|
134
|
92
|
5C
|
\
|
反斜槓 |
01011101
|
135
|
93
|
5D
|
]
|
閉方括號 |
01011110
|
136
|
94
|
5E
|
^
|
脫字符 |
01011111
|
137
|
95
|
5F
|
_
|
下劃線 |
01100000
|
140
|
96
|
60
|
`
|
開單引號 |
01100001
|
141
|
97
|
61
|
a
|
小寫字母a |
01100010
|
142
|
98
|
62
|
b
|
小寫字母b |
01100011
|
143
|
99
|
63
|
c
|
小寫字母c |
01100100
|
144
|
100
|
64
|
d
|
小寫字母d |
01100101
|
145
|
101
|
65
|
e
|
小寫字母e |
01100110
|
146
|
102
|
66
|
f
|
小寫字母f |
01100111
|
147
|
103
|
67
|
g
|
小寫字母g |
01101000
|
150
|
104
|
68
|
h
|
小寫字母h |
01101001
|
151
|
105
|
69
|
i
|
小寫字母i |
01101010
|
152
|
106
|
6A
|
j
|
小寫字母j |
01101011
|
153
|
107
|
6B
|
k
|
小寫字母k |
01101100
|
154
|
108
|
6C
|
l
|
小寫字母l |
01101101
|
155
|
109
|
6D
|
m
|
小寫字母m |
01101110
|
156
|
110
|
6E
|
n
|
小寫字母n |
01101111
|
157
|
111
|
6F
|
o
|
小寫字母o |
01110000
|
160
|
112
|
70
|
p
|
小寫字母p |
01110001
|
161
|
113
|
71
|
q
|
小寫字母q |
01110010
|
162
|
114
|
72
|
r
|
小寫字母r |
01110011
|
163
|
115
|
73
|
s
|
小寫字母s |
01110100
|
164
|
116
|
74
|
t
|
小寫字母t |
01110101
|
165
|
117
|
75
|
u
|
小寫字母u |
01110110
|
166
|
118
|
76
|
v
|
小寫字母v |
01110111
|
167
|
119
|
77
|
w
|
小寫字母w |
01111000
|
170
|
120
|
78
|
x
|
小寫字母x |
01111001
|
171
|
121
|
79
|
y
|
小寫字母y |
01111010
|
172
|
122
|
7A
|
z
|
小寫字母z |
01111011
|
173
|
123
|
7B
|
{
|
開花括號 |
01111100
|
174
|
124
|
7C
|
|
|
垂線 |
01111101
|
175
|
125
|
7D
|
}
|
閉花括號 |
01111110
|
176
|
126
|
7E
|
~
|
波浪號 |
01111111
|
177
|
127
|
7F
|
DEL (delete)
|
刪除
|
由於各個國家的編碼方式不一樣,在進行解碼的時候需要不同的方法。 正在這時,大天使加百列及時出現了——一個叫 ISO(國際標誰化組織)的國際組織決定着手解決這個問題。他們採用的方法很簡單:廢了所有的地區性編碼方案,重新搞一個包括了地球上所有文化、所有字母 和符號的編碼!他們打算叫它"Universal Multiple-Octet Coded Character Set",簡稱 UCS, 俗稱 "UNICODE"。
UNICODE 開始制訂時,計算機的存儲器容量極大地發展了,空間再也不成爲問題了。於是 ISO 就直接規定必須用兩個字節,也就是16位來統一表示所有的字符,對於ascii裏的那些“半角”字符,UNICODE 包持其原編碼不變,只是將其長度由原來的8位擴展爲16位,而其他文化和語言的字符則全部重新統一編碼。由於"半角"英文符號只需要用到低8位,所以其高 8位永遠是0,因此這種大氣的方案在保存英文文本時會多浪費一倍的空間。
這時候,從舊社會裏走過來的程序員開始發現一個奇怪的現象:他們的strlen函數靠不住了,一個漢字不再是相當於兩個字符了,而是一個!是的,從 UNICODE 開始,無論是半角的英文字母,還是全角的漢字,它們都是統一的"一個字符"!同時,也都是統一的"兩個字節",請注意"字符"和"字節"兩個術語的不 同,“字節”是一個8位的物理存貯單元,而“字符”則是一個文化相關的符號。在UNICODE 中,一個字符就是兩個字節。一個漢字算兩個英文字符的時代已經快過去了。
從前多種字符集存在時,那些做多語言軟件的公司遇上過很大麻煩,他們爲了在不同的國家銷售同一套軟件,就不得不在區域化軟件時也加持那個雙字節字符集咒 語,不僅要處處小心不要搞錯,還要把軟件中的文字在不同的字符集中轉來轉去。UNICODE 對於他們來說是一個很好的一攬子解決方案,於是從 Windows NT 開始,MS 趁機把它們的操作系統改了一遍,把所有的核心代碼都改成了用 UNICODE 方式工作的版本,從這時開始,WINDOWS 系統終於無需要加裝各種本土語言系統,就可以顯示全世界上所有文化的字符了。
但是,UNICODE 在制訂時沒有考慮與任何一種現有的編碼方案保持兼容,這使得 GBK 與UNICODE 在漢字的內碼編排上完全是不一樣的,沒有一種簡單的算術方法可以把文本內容從UNICODE編碼和另一種編碼進行轉換,這種轉換必須通過查表來進行。
如前所述,UNICODE 是用兩個字節來表示爲一個字符,他總共可以組合出65535不同的字符,這大概已經可以覆蓋世界上所有文化的符號。如果還不夠也沒有關係,ISO已經準備 了UCS-4方案,說簡單了就是四個字節來表示一個字符,這樣我們就可以組合出21億個不同的字符出來(最高位有其他用途),這大概可以用到銀河聯邦成立 那一天吧!
UNICODE 來到時,一起到來的還有計算機網絡的興起,UNICODE 如何在網絡上傳輸也是一個必須考慮的問題,於是面向傳輸的衆多 UTF(UCS Transfer Format)標準出現了,顧名思義,UTF8就是每次8個位傳輸數據,而UTF16就是每次16個位,只不過爲了傳輸時的可靠性,從UNICODE到 UTF時並不是直接的對應,而是要過一些算法和規則來轉換。