背景

Ruby直到1.9版本才很好的支持了多字节编码,本文简单总结了今天学习的关于Ruby编码方面的知识。

字符串可以使用不同的编码

在.NET中字符串的编码是一致的,Ruby允许字符串有不同的编码,当时我就在想:如果两个不同编码的字符串相加会出现什么结果?

测试程序

 1 # coding: utf-8
 2
 3 str_utf8 = "hi 段"
 4 puts str_utf8.size                                # 4
 5 puts str_utf8.bytesize                            # 6
 6 puts str_utf8 .encoding                         # UTF-8
 7 str_utf8.each_byte {|b| print "%02X," % [b]}      # 68,69,20,E6,AE,B5,
 8 puts
 9
10 puts
11
12 str_gb2312 = "hi 段".encode("gb2312")
13 puts str_gb2312.size                            # 4
14 puts str_gb2312.bytesize                        # 5
15 puts str_gb2312 .encoding                         # GB2312
16 str_gb2312.each_byte {|b| print "%02X," % [b]}     # 68,69,20,B6,CE,
17 puts

输出结果

1 4
2 6
3 UTF-8
4 68,69,20,E6,AE,B5,
5
6 4
7 5
8 GB2312
9 68,69,20,B6,CE,

备注:UTF-8对英文采用1个字节,对中文采用三个字节。GB2312对英文采用1个字节,对中文采用两个字节。

编码转换

编码转换可以采用String::encode("目标编码名称")来完成,如果编码之间的转换兼容,返回编码后的字符串,否则会抛出编码转换异常。

测试程序

1 begin
2     puts "段".encode("ascii")
3 rescue Exception => e
4     puts e.class
5 end
6
7 puts "段".encode("gb2312")

输出结果

1 Encoding::UndefinedConversionError
2 段

备注:encode会返回一个和元字符串序列一样的字符串序列,只是内部的字节序列改变了。

编码强制

编码强制是指在不改变字节序列的情况下改变对字节的解释方式,编码强制:String::force_encoding("强制编码")。

测试程序

 1 utf8_str = "\xE6\xAE\xB5".encode("utf-8")
 2 puts utf8_str.encoding() # UTF-8
 3 puts utf8_str.size # 1
 4 puts utf8_str.bytesize # 3
 5
 6 ascii_str = "\xE6\xAE\xB5".force_encoding("ascii")
 7 puts ascii_str.encoding() # US-ASCII
 8 puts ascii_str.size # 3
 9 puts ascii_str.bytesize # 3
10 puts ascii_str.valid_encoding? # false

输出结果

1 UTF-8
2 1
3 3
4 US-ASCII
5 3
6 3
7 false

备注:String::valid_encoding?可以判定是否是有效的强制。

不同编码的字符串相加后是啥结果?

这个问题的答案很简单:如果两个字符串的编码兼容,则返回字符集最大的编码,否则跑出不兼容异常。你可以自己检查兼容性:Encoding.compatible?。

测试程序

1 str_ascii = "hi ".encode("ascii")
2 str_utf8 = "段"
3 puts str_ascii.encoding
4 puts str_utf8.encoding
5 puts Encoding.compatible?(str_ascii.encoding, str_utf8.encoding)
6 puts (str_ascii + str_utf8).encoding
7 puts (str_utf8 + str_ascii).encoding

运行结果

1 US-ASCII
2 UTF-8
3 UTF-8
4 UTF-8
5 UTF-8

一直没使用过的\u和\x

几乎所有的语言都支持这两个转义字符,允许我们使用\uXXXX指定Unicode码点对于的字符,通用也运行我们使用\xXX指定字节。

测试程序

1 puts "段" # 段
2 puts "\xE6\xAE\xB5" # 段
3 puts "\u6BB5" # 段

输出结果

1 # 段
2 # 段
3 # 段

使用Sublime开发Ruby时,输出到控制台的字符串为啥不能使用多种编码?

测试程序

1 puts "段"
2 puts "段".encode("GB2312")

在Sublime中的输出结果

1 [Decode error - output not utf-8]

在控制台的输出结果

原因分析

Sublime之所以失败是因为Sublime重定位了默认标准输出流,而重定位后的流不支持混合多种编码,说白了:你没法在一个文件中保存两种编码的字符串。

备注:Sublime中的失败不是Ruby导致的,是Sublime自身的问题。

如何解决?

Sublime默认只能接收UTF8编码,因此必须转换为UTF8编码。

1 # 默认是UTF8编码,不用处理。
2 puts "段"
3 # 执行windows命令必须使用GB2312编码。
4 command = "echo 段".encode("GB2312")
5 # 命令执行的结果想输出到Sublime必须使用UTF8编码。
6 puts `#{command}`.encode("utf-8")

输出结果

1  # 输出结果
2  段
3  段

备注

字符串、字符集和编码算是刚入门,有机会还得继续学习。

转载于:https://www.cnblogs.com/happyframework/p/3275367.html

Ruby:字符集和编码学习总结相关推荐

  1. 面试题字符集和编码区别_您和理想工作之间的一件事-编码面试!

    面试题字符集和编码区别 A recruiter calls you for a position with your dream company. You get extremely excited ...

  2. 创建数据库,指定数据库的字符集和编码顺序

    创建数据库,指定它的字符集和编码顺序 create database {数据库名称} CHARACTER SET {字符集} COLLATE {排序规则} 举例: create database co ...

  3. 你不知道的 字符集和编码(编码字符集与字符集编码)

    我的上篇文章,有朋友提出字符集和编码的区别,我在此立文和大家讨论下 常说的字符集和编码区别,其实就是编码字符集和字符集编码的区别,其实,单单如果只是说字符集,没有任何编码的概念的话,那么字符集其实仅仅 ...

  4. 字符集和编码规范:ASCII,Unicode和UTF-8, latin1,BIG5,GBK

    字符集和编码方式:ASCII,Unicode和UTF-8, latin1,BIG5,GBK 参考: 字符集 字符集编码详解 一. ASCII码 我们知道,在计算机内部,所有的信息最终都表示为一个二进制 ...

  5. [转]各种字符集和编码详解

    在软件的编码和实现中,我们可能会碰到个 一个比较头疼的问题--编码,不同字符间的编码和解码,你确定了解各种字符的编码吗?一个朋友问到了我这个问题,我虽然能回答一两个出来,但是感觉已经有点模糊,混乱了, ...

  6. 各种字符集和编码详解

    在软件的编码和实现中,我们可能会碰到个 一个比较头疼的问题--编码,不同字符间的编码和解码,你确定了解各种字符的编码吗?一个朋友问到了我这 个问题,我虽然能回答一两个出来,但是感觉已经有点模糊,混乱了 ...

  7. 漫画:什么是字符集和编码?ASCII、UTF-8、UTF-16、UTF-32 又是什么?

    当天下午 -------- 在计算机底层,比如说你的名字"小萌"在计算机中并不是文字的形式,而是一串二进制数字,如"011001100110-" 人类只认识文字 ...

  8. python爬虫之字符集和编码

    python requests的content与text方法的区别** requests对象的get和post方法都会返回一个Response对象,这个对象里面存的是服务器返回的所有信息,包括响应头, ...

  9. 【字符集】字符集和编码知识【转】

    字符是各种文字和符号的总称,包括各国家文字.标点符号.图形符号.数字等.字符集是多 个字符的集合,字符集种类较多,每个字符集包含的字符个数不同,常见字符集名称:ASCII 字符集.ISO 8859字符 ...

最新文章

  1. wxWidgets:wxSplashScreen 示例
  2. 批处理启动vm虚拟机服务 vm12启动无界面启动vm虚拟机系统 windows上如何操作服务 sc net启动关闭服务...
  3. BootStrap table 传递搜索参数
  4. et中计算机的快捷键,ET制版快捷键
  5. (学习笔记)图像处理——同态滤波
  6. HttpClient 4.2.3 (GA) 这些名字里面都有GA,GA代表什么意思啊?
  7. 物理层(网线)、数据链路层(交换机)、网络层(IP协议、ARP协议、ICMP协议、路由器)、VLAN(虚拟局域网)、HSRP协议、ACL、NAT
  8. 算力进化!新华三打造“一体·两中枢”全新智慧计算体系
  9. 领存发布Z3系列2.5寸SATA一键自毁固态硬盘
  10. 2022支付宝集五福攻略,一天20张不是事
  11. 还在找各种便签软件?Windows10自带的便签足矣
  12. RGB图像转换为灰度图像的原理
  13. Panic的概念和使用
  14. 如何禁止百度自动转码?
  15. 2021年8月互联网舆情热点事件报告
  16. 前端开发学习路径之阶段七:BootStrap详解
  17. 月饼大战白热化,保险公司也来Battle了!
  18. JSP判断radio是否选择和传值栗子(测试应聘人员能力自动计算分数)
  19. Oracle函数--日期函数
  20. 自动控制原理是计算机学科吗,自动控制原理是自动化学科的重要理论基础(基本概念).doc...

热门文章

  1. 分享5个冷门而超级实用的在线网站,大家赶紧来看看吧!
  2. Linux中Shell循环结构for用法笔记
  3. 这几款前端必备构建工具合辑,我们帮你整理好了!
  4. jio文件 久其_功能强大的Windows文件管理器工具
  5. python爬虫--如何爬取翻页url不变的网站
  6. 数据可视化 信息可视化_可视化哲学的黎明
  7. 苹果风格ui_苹果如何使Soft-UI成为未来
  8. 一份 2.5k star 的《React 开发思想纲领》
  9. 魅族魅蓝mirror简单打开usb调试模式的步骤
  10. ServletContextListener在Springboot中的使用