首页
社区
课程
招聘
[讨论]关于UTF-8编码方式的一个深度问题。
发表于: 2013-6-10 22:03 7045

[讨论]关于UTF-8编码方式的一个深度问题。

2013-6-10 22:03
7045
大家知道UTF是按照上面这种方式对UCS进行编码的,对于原来的前128个字符,保持不变。我的问题是为什么需要按照模板加那么多位,具体有什么好处。为什么不能直接原来的ascii保持一个字节不变,后面的直接按ucs2 两个字节代表一个字符,不就可以了吗?何必要编码出来三个字节,四个字节。知道的大牛麻烦说一声啊,想知道好久了,谢谢。


[培训]内核驱动高级班,冲击BAT一流互联网大厂工作,每周日13:00-18:00直播授课

上传的附件:
收藏
免费 0
支持
分享
最新回复 (14)
雪    币: 1711
活跃值: (516)
能力值: ( LV12,RANK:200 )
在线值:
发帖
回帖
粉丝
2
每组都有编码使得当读到序列中任意一个字节的时候,都可以知道该字符是不是一个独立的字符。比如你读到一个字节是0xxxxxxx,如果按你设想的那样编码,你无法知道该字节是属于一个ASCII,还是一个UCS的一部分。有了UTF的分组,读到0xxxxxxx就必然是ASCII,读到10xxxxxx就知道是某个多字节字符的一部分。
2013-6-10 23:32
0
雪    币: 6
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
3
谢谢supercolin回答,但是我是这样理解的,比如我们可以规定如果小于128的字节那么就当做ascii处理,然后其他的ucs2按2字节、2字节这样处理,就和处理我们的GBK编码一样,这样不也可以吗?这样也起码能编码6万多个字符。
2013-6-10 23:53
0
雪    币: 291
活跃值: (213)
能力值: ( LV12,RANK:210 )
在线值:
发帖
回帖
粉丝
4
6万多个字符有什么用?只存汉字都不够,Unicode就失去意义了。我印象里UTF-8最多可以有6个还是多少个字节的,这样才能保证能够存放绝大多数语言的字符。

UTF-8这种编码方式的独到之处在于,如果给你一个字符流序列,无论从序列的哪个字节(不是字符!可以是字符中间的任意字节)出发,你都可以准确定位到下一个字符的开始位置。你的方式就失去这个能力了,不知道你有没有真正理解这一点。

最后,不要看到windows有unicode有wchar_t,就以为windows里面所有的“unicode”字符都是2字节的,也有4字节甚至更多长度的字符存在,当然,都是一些很罕见的字符。
2013-6-11 00:37
0
雪    币: 6
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
5
这个好像不可以吧,只能从当前字符编码的第一个字节能定位到下一个字符,其他字节是无法定位的,因为一个字符包含几字节的信息在第一个字节里存放,你想想看。
2013-6-11 02:44
0
雪    币: 218
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
6
Unicode有17个语言平面,每个平面FFFFh个字符,所以最大值为10FFFF
第0平面为基本多文种平面,就是我们常用的WCHAR
2013-6-12 18:06
0
雪    币: 952
活跃值: (1821)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
7
多语言其实是个很麻烦的事 Unicode解决不了多语言混用 utf8 可以
2013-6-12 20:13
0
雪    币: 6
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
8
可是我的问题没搞明白
2013-6-12 21:31
0
雪    币: 1711
活跃值: (516)
能力值: ( LV12,RANK:200 )
在线值:
发帖
回帖
粉丝
9
需要向前回朔才能得到完整的字符。还是我举的例子,按照你设想的编码方式,比如有个3字节序列是这样
..., 1xxxxxxx, 0xxxxxxx, 1xxxxxxx, ...
看到0xxxxxxx,你无法判断它是一个单独的ASCII字符,还是和前面的1xxxxxxx组合起来的2字节表示一个字符。你无法判断哪里是一个字符的开始,因为每个字节的所有bit都被用来表示字符编码本身而不是分组了。
再来看UTF8,不管你读到序列的哪个字节,都可以很容易判断出如何解码:
如果是0xxxxxxx,那就是ASCII字符;
如果是10xxxxxx,那知道是某个多字节字符的一部分,向先查找,直到找到11开头的一个字节,于是知道了这是几字节字符。
还有一个原因就是两字节最多只能表示65535个字符,也就是UCS-2。可世界上所有语言还有乱七八糟符号什么的超过了这个范围,所以才有了UCS-4,那样的话两字节是不够的。UTF-8的6字节编码有31个有效位,正好是UCS-4的上限,因此能表示目前规范涵盖的所有字符了。
另外我查了一下资料,UTF-8也被限制了范围(RFC 3629),理论上的各种编码组合中有些并不会被在实际中采用。
另外想说一点关于工业标准的制定。最近十几年工业标准的指定比以前考虑得更加周到,因为发展太迅速,标准制定者往往会考虑未来的因素,容量是否足够,扩展性如何,兼容性如何,是否便于处理(软、硬件)。商业因素也会被作为考虑标准之一,不过现在商业垄断越来越困难了。
2013-6-14 10:26
0
雪    币: 218
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
10
UTF8是Unicode的一种编码表达方式,他们两者的关系就类似二进制和十进制一样,从何而来的Unicode无法解决多语言混用而UTF8就可以
2013-6-14 10:49
0
雪    币: 952
活跃值: (1821)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
11
Unicode存在区域问题,比如网页上就有这问题,中文和很多小语种就不在一个区域,用Unicode就不能同时显示 而utf8不存在这个问题,不区分区域,所有语言都在同一编码里,所以网页要么和本地化编码,要么用utf8
2013-6-14 10:59
0
雪    币: 6
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
12
看完supercolin大哥说的后,我终于明白了,再次感谢所有的人。我大致想总结下。这下终于把所有编码的来龙去脉搞清楚了。我想我的想法其实也许对大家有用:
1、首先,其实我的想法也是对的,就是对ASCII前0-127用一个字节表示,后面的用ucs2 表示,但是这样有一个问题就是正如supercolin大哥说的,没办法分辨里面的单个字节是属于ASCII还是属于UCS2分组字节中的某个字节,除非我们定死,即全部规定用2个或者4个字节来表示一个编码。即我们可以直接用USC2来编码包括ASCII之内的所有编码,都用2个字节表示,我们在记事本保存的时候编码选项中就有UNICODE这一项,如果这样保存一段汉字的话,大小会比使用UTF8编码小很多。但是如果保存英文字符的话,就成了2倍的大小了。
2、要解决我上面的问题,即采用一种变长的编码对UNICODE进行再编码,即发明了所谓的UTF8(UNICODE转换格式)编码,因为需要附加信息来表示一些比如编码长度等信息,以及编码标记,因此增加了原来UNICODE的编码长度。
3、有人常说UTF8解决了多语言混排,其实应该不是这样的,因为如果使用UNICODE也支持多语言混排。UTF8只是解决了变长字节编码的混排。
3、UTF8其实为了实现英文字符的单字节编码,增加了其他字符的编码长度,因此其实是方便了老外。对于我们汉字等语言来说,就是增加了编码长度。所以我们不能滥用UTF8编码,大家看看国内的一些门户网站的编码,都是用了GBK,而不是UTF8。
2013-6-15 21:05
0
雪    币: 218
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
13
我怎么觉得你那个Unicode不能同时显示是说的MBCS
要不你给个例子吧
2013-6-16 04:24
0
雪    币: 1847
活跃值: (1806)
能力值: ( LV12,RANK:230 )
在线值:
发帖
回帖
粉丝
14
我也认为这句话不正确
2013-6-16 09:53
0
雪    币: 6
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
15
那兄弟们认为我说的对吗?
2013-6-16 14:40
0
游客
登录 | 注册 方可回帖
返回
//