字符集和字符编码

本文从ASCII码出发,探讨了中文编码标准的发展历程,包括GB2312、GBK、GB18030等,并介绍了Unicode及其多种编码形式如UTF-8、UTF-16等。

我们需要了解的最早编码是ASCII码。它用7个二进制位来表示,由于那个时期生产的大多数计算机使用8位大小的字节,因此用户不仅可以存放所有可能的ASCII字符,而且有整整一位空余下来。如果你技艺高超,可以将该位用做自己离奇的目的:WordStar中那个发暗的灯泡实际上设置这个高位,以指示一个单词中的最后一个字母,同时这也宣示了WordStar只能用于英语文本。由于字节有多达8位的空间,因此许多人在想:“呀!我们可以把128~255之间的编码用做个人的应用目的。”问题在于,同时产生这种想法的人相当多,而且在128~255之间的各个位置上应该存放什么这一问题上,真是仁者见仁智者见智。事实上,只要人们开始在美国以外的地方购买计算机,那么各种各样的不同OEM字符集都会进入规划设计行列,并且各人都会根据自己的需要使用高位的128个字符。如此一来,甚至在同语种的文档之间就不容易实现互换。 ASCII可被扩展,最优秀的扩展方案是ISO 8859-1,通常称之为Latin-1。Latin-1包括了足够的附加字符集来写基本的西欧语言。最后,这个人人参与的OEM终于以ANSI标准的形式形成文件。在ANSI标准中,每个人都认同如何使用低端的128个编码,这与ASCII相当一致。不过,根据所在国籍的不同,处理编码128以上的字符有许多不同的方式。这些不同的系统称为代码页。同时,甚至更为令人头疼的事情正在逐步上演,亚洲国家的字符表有成千上万个字符,这样的字符表是用8位二进制无法表示的。该问题的解决通常有赖于称为DBCS(double byte character set,双字节字符集)的繁杂字符系统。作用:表语英语及西欧语言。位数:ASCII是用7位表示的,能表示128个字符;其扩展使用8位表示,表示256个字符。范围:ASCII从00到7F,扩展从00到FF。

..............................................................................................................................................................................................

为了处理汉字,设计了用于简体中文的GB2312和用于繁体中文的big5

GB2312(1980)一共收录了7445个字符,包括6763个汉字和682个其它符号。汉字区的内码范围高字节从B0-F7,低字节从A1-FE,占用的码位是72*94=6768。其中有5个空位是D7FA-D7FEBIG5字符集是目前台湾、香港地区普遍使用的一种繁体汉字的编码标准,包括440个符号,一级汉字5401个、二级汉字7652个,共计13060个汉字

GB2312支持的汉字太少。1995年的汉字扩展规范GBK1.0收录了21886个符号,它是GB2312的扩展,加入对繁体字的支持,兼容GB2312。

ASCIIGB2312GBK,这些编码方法是向下兼容的,即同一个字符在这些方案中总是有相同的编码,后面的标准支持更多的字符。在这些编码中,英文和中文可以统一地处理。区分中文编码的方法是高字节的最高位不为0。按照程序员的称呼,GB2312GBK都属于双字节字符集 (DBCS)

2000年的GB18030是取代GBK1.0的正式国家标准。该标准收录了27484个汉字,同时还收录了藏文、蒙文、维吾尔文等主要的少数民族文字。从汉字字汇上说,GB18030GB13000.120902个汉字的基础上增加了CJK扩展A6582个汉字(Unicode 0x3400-0x4db5),一共收录了27484个汉字。CJK就是中日韩的意思GB18030的编码采用单字节、双字节和4字节方案。其中单字节、双字节和GBK是完全兼容的。4字节编码的码位就是收录了CJK扩展A6582个汉字。

..............................................................................................................................................................................................

Unicode和UCS是两个独立的组织分别制定的一套编码标准,但是因为历史的原因,这两套标准是完全一样的。它包含了世界上大多数可书写的字符系统。

对于大部分常用字符,比如Unicode编码只占一个字节大小的英语字母,占两个字节大小汉字,都用4个字节来储存太奢侈了。另外,如果都用4字节直接表示,就不可避免的出现为0的字节。而我们知道,在C语言中,0x00的字节就是'\0',表示的是一个字符串(char字符串,非wchar_t)的结束,换句话说,C风格的char字符串无法表示Unicode。

因为类似的种种问题,为Unicode在计算机中的编码方法出现了,这就是UTF。所对应的,为UCS编码实现的方式也有自己的说法。一般来说,UTF-x,x表示这套编码一个单位至少占用x位,因为Unicode最长达到32位,所以UTF-x通常是变长的——除了UTF-32;而UCS-y表示一个单位就占用y个字节,所以能表示当今Unicode的UCS-y只有UCS-4,但是因为历史的原因,当Unicode还没那么庞大的时候,2个字节足够表示,所以有UCS-2,现在看来,UCS-2所能表示的Unicode只是当今Unicode的一个子集。

Unicode字符集有多个编码方式,分别是UTF-8,UTF-16,UTF-32和UTF-7编码。

UTF-8是一套“聪明”的编码,可能用1,2,3,4个字节表示。通过UTF-8的算法,每一个字节表示的信息都很明确:这是不是某个Unicode编码的第一个字节;如果是第一个字节,这是一个几位Unicode编码。这种“聪明”被称为UTF-8的自我同步,也是UTF-8成为网络传输标准编码的原因。另外,UTF-8也不会出现0字节,所以可以表示为char字符串,所以可以成为系统的编码。Linux系统默认使用UTF-8编码。

UTF-16用2个字节或者4个字节表示。在2个字节大小的时候,跟UCS-2是一样的。UTF-16不像UTF-8,没有自我同步机制,所以,编码大位在前还是小位在前,就成了见仁见智的问题。Windows中的wchar_t就是采用UCS-2BE编码,BE指的是大位在后。需要指出的是,C++标准中对wchar_t的要求是要能表示所有系统能识别的字符。Windows自称支持Unicode,但是其wchar_t却不能表示所有的Unicode,由此违背了C++标准。

UTF-32在目前阶段等价于UCS-4,都用定长的4个字节表示。UTF-32同样存在BE和LE的问题。Linux的wchar_t编码就是UTF-32BE。在16位以内的时候,UTF-32BE的后两位(前两位是0x00 0x00)等价于UTF-16BE也就等价于UCS-2BE。


..............................................................................................................................................................................................

理解:1.字符集与字符编码的区别。

        2.宽字符不一定是Unicode. Unicode只是宽字符编码的一种实现。 Unicode被认为是C编程环境中的宽字符。

### 字符集字符编码的区别详解 字符集(Character Set)字符编码(Character Encoding)是计算机处理文本时两个密切相关但不同的概念。以下是它们的详细区别: #### 1. 字符集的定义 字符集是指一组特定的字符集合,它定义了哪些字符可以被表示。例如,ASCII字符集包含128个字符,包括英文字母、数字一些符号[^3]。字符集的作用是规定“有哪些字符可用”,而不涉及这些字符如何存储在计算机中。 #### 2. 字符编码的定义 字符编码则是将字符集中的每个字符映射为计算机能够理解的二进制形式的过程。换句话说,字符编码定义了“如何用字节表示字符”。例如,在ASCII编码中,字母`A`被编码为`01000001`[^3]。字符编码的作用是确保字符能够在计算机中正确存储传输。 #### 3. 关系与区别 - **关系**:字符集字符编码的基础。一个字符编码方案必须基于某个字符集。例如,UTF-8是一种字符编码方案,它基于Unicode字符集。 - **区别**: - 字符集仅定义了字符的集合,而字符编码则定义了这些字符如何被表示为字节序列。 - 同一个字符集可以有多种编码方式。例如,Unicode字符集可以通过UTF-8、UTF-16或UTF-32进行编码[^1]。 - 字符编码还决定了一个字符占用多少字节。例如,在GBK编码中,中文字符通常占用2个字节,而在UTF-8编码中,中文字符可能占用3个字节[^4]。 #### 4. 实际应用示例 以下是一个简单的Python代码示例,展示如何使用字符编码进行字符串的编码解码操作: ```python # 原始字符串 original_string = "你好,世界!" # 使用UTF-8编码将字符串转换为字节 encoded_bytes = original_string.encode('utf-8') print(f"UTF-8编码后的字节: {encoded_bytes}") # 使用GBK编码将字符串转换为字节 encoded_bytes_gbk = original_string.encode('gbk') print(f"GBK编码后的字节: {encoded_bytes_gbk}") # 将字节解码回字符串 decoded_string = encoded_bytes.decode('utf-8') print(f"解码后的字符串: {decoded_string}") ``` #### 5. 总结 字符集字符编码是文本处理中不可或缺的概念。字符集定义了字符的范围,而字符编码则定义了字符的存储方式。在实际开发中,选择合适的字符集编码方式对于确保数据的正确性兼容性至关重要。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值