与ARGF混淆#set_encoding

Aru*_*hit 2 ruby encoding character-encoding

ARGF.set_encoding 说:

如果指定了单个参数,则从ARGF读取的字符串将使用指定的编码进行标记.

如果给出由冒号分隔的两个编码名称,例如"ascii:utf-8",则将读取的字符串从第一编码(外部编码)转换为第二编码(内部编码),然后使用第二编码进行标记.

所以我尝试了以下内容:

p RUBY_VERSION
p ARGF.external_encoding
ARGF.set_encoding('ascii')
p ARGF.readlines($/)
Run Code Online (Sandbox Code Playgroud)

输出:

D:\Rubyscript\My ruby learning days>ruby true.rb a.txt
"2.0.0"
#<Encoding:IBM437>
["Hi! How are you?\n", "I am doing good,thanks."]

p RUBY_VERSION
p ARGF.external_encoding
ARGF.set_encoding(ARGF.external_encoding,'ascii')
p ARGF.readlines($/)
Run Code Online (Sandbox Code Playgroud)

输出:

D:\Rubyscript\My ruby learning days>ruby true.rb a.txt
"2.0.0"
#<Encoding:IBM437>
["Hi! How are you?\n", "I am doing good,thanks."]
Run Code Online (Sandbox Code Playgroud)

未找到编码更改.所以请告诉我正确的方法.

Ari*_*iao 5

编码IBM437ASCII(和UTF-8)具有相同的ASCII字符字节序列.所以你不会看到它的区别String#inspect.但是,您可以检查String#encoding输入字符串的值.

p RUBY_VERSION
p ARGF.external_encoding
ARGF.set_encoding(ARGF.external_encoding,'ascii')
p ARGF.readlines($/).map{|s| s.encoding}
Run Code Online (Sandbox Code Playgroud)

在Ruby(1.9及更高版本)中,String是一个用某些编码标记的字节序列.您可以从中获取编码String#encoding.

所以中文"中"可以用不同的方式表示:

e4 b8 ad          # tagged with encoding UTF-8
d6 d0             # tagged with encoding GBK
2d 4e             # tagged with encoding UTF-16le
Run Code Online (Sandbox Code Playgroud)

我将始终用UTF-8编写脚本,也就是说,我脚本的内部编码是UTF-8.有时我想处理用GBK编码的文本文件(例如名为"a.txt"并具有内容"中").然后我可以为IO对象设置外部编码和内部编码,Ruby将为我做转换.

ARGF.set_encoding('GBK', 'UTF-8')
str = ARGF.readline
puts str.encoding

# run             $ script.rb a.txt
Run Code Online (Sandbox Code Playgroud)

Ruby "\xd6\xd0"从"a.txt" 读取,因为我已将外部编码指定为GBK,所以它使用编码GBK标记数据.我已经将内部编码指定为UTF-8,因此Ruby执行从GBK字节序列到UTF-8的转换,这导致"\xe4\xb8\xad"标记为UTF-8.这个字符串与我脚本中的其他字符串具有相同的编码,因此我可以轻松使用它.

这很有用,因为当两个String操作数具有不同的不兼容编码时,许多String方法都会失败.例如:

# encoding: utf-8
a = "?"                  # tagged with UTF-8
b = "?".encode('gbk')    # tagged with GBK
puts a + b
#=> Encoding::CompatibilityError: incompatible character encodings: UTF-8 and GBK
Run Code Online (Sandbox Code Playgroud)