use*_*146 55 ruby csv string encoding utf-8
我正在使用ruby 1.9.2
我正在尝试解析包含一些法语单词的CSV文件(例如spécifié)并将内容放在MySQL数据库中.
当我从CSV文件中读取行时,
file_contents = CSV.read("csvfile.csv", col_sep: "$")
Run Code Online (Sandbox Code Playgroud)
这些元素以ASCII-8BIT编码的字符串形式返回(spécifié变为sp\xE9cifi\xE9),然后像"spécifié"这样的字符串未正确保存到我的MySQL数据库中.
Yehuda Katz说ASCII-8BIT实际上是"二进制"数据,这意味着CSV不知道如何读取适当的编码.
所以,如果我尝试使CSV强制编码如下:
file_contents = CSV.read("csvfile.csv", col_sep: "$", encoding: "UTF-8")
我收到以下错误
ArgumentError: invalid byte sequence in UTF-8:
Run Code Online (Sandbox Code Playgroud)
如果我回到我原来的ASCII-8BIT编码字符串并检查我的CSV读取为ASCII-8BIT的字符串,它看起来像"非sp\xE9cifi\xE9"而不是"非spécifié".
这样做我无法将"Non sp\xE9cifi\xE9"转换为"非spécifié"
"Non sp\xE9cifi\xE9".encode("UTF-8")
因为我收到这个错误:
Encoding::UndefinedConversionError: "\xE9" from ASCII-8BIT to UTF-8
,
Katz指出会发生这种情况,因为ASCII-8BIT实际上并不是一个正确的字符串"编码".
问题:
mu *_*ort 60
deceze是对的,即ISO8859-1(AKA Latin-1)编码文本.试试这个:
file_contents = CSV.read("csvfile.csv", col_sep: "$", encoding: "ISO8859-1")
Run Code Online (Sandbox Code Playgroud)
如果这不起作用,您可以使用以下内容Iconv
来修复单个字符串:
require 'iconv'
utf8_string = Iconv.iconv('utf-8', 'iso8859-1', latin1_string).first
Run Code Online (Sandbox Code Playgroud)
如果latin1_string
是"Non sp\xE9cifi\xE9"
,那么utf8_string
会"Non spécifié"
.此外,Iconv.iconv
可以一次取消整个数组:
utf8_strings = Iconv.iconv('utf-8', 'iso8859-1', *latin1_strings)
Run Code Online (Sandbox Code Playgroud)
使用较新的Rubies,您可以执行以下操作:
utf8_string = latin1_string.force_encoding('iso-8859-1').encode('utf-8')
Run Code Online (Sandbox Code Playgroud)
其中,latin1_string
认为它是ASCII-8BIT,但确实是在ISO 8859.
knu*_*nut 26
使用ruby> = 1.9即可使用
file_contents = CSV.read("csvfile.csv", col_sep: "$", encoding: "ISO8859-1:utf-8")
Run Code Online (Sandbox Code Playgroud)
这ISO8859-1:utf-8
意味着:csv文件是ISO8859-1编码的,但将内容转换为utf-8
如果您更喜欢更详细的代码,可以使用:
file_contents = CSV.read("csvfile.csv", col_sep: "$",
external_encoding: "ISO8859-1",
internal_encoding: "utf-8"
)
Run Code Online (Sandbox Code Playgroud)
归档时间: |
|
查看次数: |
53253 次 |
最近记录: |