ruby - 如何在不转换为不同编码的情况下替换 Ruby 中的 UTF-8 错误?

标签 ruby string unicode encoding utf-8

为了将字符串转换为 UTF-8 并替换所有编码错误,您可以这样做:

str.encode('utf-8', :invalid=>:replace)

唯一的问题是如果 str 已经是 UTF-8 则它不起作用,在这种情况下仍然存在任何错误:

irb> x = "foo\x92bar".encode('utf-8', :invalid=>:replace)
=> "foo\x92bar"
irb> x.valid_encoding?
=> false

引用Ruby Docs :

Please note that conversion from an encoding enc to the same encoding enc is a no-op, i.e. the receiver is returned without any changes, and no exceptions are raised, even if there are invalid bytes.

明显的解决方法是先转换为不同的 Unicode 编码,然后再转换回 UTF-8:

str.encode('utf-16', :invalid=>:replace).encode('utf-8')

例如:

irb> x = "foo\x92bar".encode('utf-16', :invalid=>:replace).encode('utf-8')
=> "foo�bar"
irb> x.valid_encoding?
=> true

有没有更好的方法在不转换为虚拟编码的情况下执行此操作?

最佳答案

Ruby 2.1 添加了一个 String#scrub做你想做的事情的方法:

2.1.0dev :001 > x = "foo\x92bar"
 => "foo\x92bar" 
2.1.0dev :002 > x.valid_encoding?
 => false 
2.1.0dev :003 > y = x.scrub
 => "foo�bar" 
2.1.0dev :004 > y.valid_encoding?
 => true 

相同的提交还更改了 encode 的行为,以便它在源和目标编码相同时工作:

2.1.0dev :005 > x = "foo\x92bar".encode('utf-8', :invalid=>:replace)
 => "foo�bar" 
2.1.0dev :006 > x.valid_encoding?
 => true 

据我所知,在 2.1 之前没有内置的方法来执行此操作(否则将不需要 scrub),因此在 2.1 发布之前您需要使用一些解决方法,并且你可以升级。

关于ruby - 如何在不转换为不同编码的情况下替换 Ruby 中的 UTF-8 错误?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/19164254/

相关文章:

ruby-on-rails - 基于第三个 HABTM 模型的标准,来自两个模型的单个 ActiveRecord 集合

c++ - 在 C++ 中将十六进制字符串转换为无符号字符

java - 如何区分数字和字符串

string - 是否有完全正确的 Unicode 支持的编程语言?

python - 使用附加字符对 UTF-8 输出中的正负符号进行编码

javascript - 值 &# 到 unicode 转换

ruby - 在 Ruby 中使用 2 个助手构造函数的惯用方法

ruby-on-rails - Rails 应用程序中的默认 Sidekiq Redis 配置

ruby-on-rails - 在 rails 的 fast_jsonapi 中将 current_user 和链接一起传递

string - 是否有正则表达式可以切换字符串中的字符大小写?