【发布时间】:2011-10-26 06:02:02
【问题描述】:
我使用的是 ruby 1.9.2
我正在尝试解析一个包含一些法语单词(例如 spécifié)的 CSV 文件,并将内容放入 MySQL 数据库中。
当我从 CSV 文件中读取行时,
file_contents = CSV.read("csvfile.csv", col_sep: "$")
元素以 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:
如果我回到原来的 ASCII-8BIT 编码字符串并检查我的 CSV 读取为 ASCII-8BIT 的字符串,它看起来像“Non sp\xE9cifi\xE9”而不是“Non spécifié”。
我无法通过这样做将“Non sp\xE9cifi\xE9”转换为“Non spécifié”
"Non sp\xE9cifi\xE9".encode("UTF-8")
因为我收到此错误:
Encoding::UndefinedConversionError: "\xE9" from ASCII-8BIT to UTF-8,
Katz 指出会发生,因为 ASCII-8BIT 并不是真正的正确字符串“编码”。
问题:
- 我可以让 CSV 以适当的编码读取我的文件吗?如果有,怎么做?
- 如何将 ASCII-8BIT 字符串转换为 UTF-8 以便在 MySQL 中正确存储?
【问题讨论】:
-
听起来文件可能不是 UTF-8 编码的;你检查过文件的实际编码了吗?
-
您的文件未以 UTF-8 编码。 UTF-8 中的 é 应该是
C3 A9,而不是E9。看起来您正在处理 ISO-8859-1。 -
我想我明白了:my_ascii_8bit_string.unpack("C*").pack("U*") 似乎有效。
-
@deceze:是的,该文件不是 UTF-8 编码的,但我想通过 ruby 来实现
-
那么正确的方法是将 CSV 读取为 ISO-8859-1 并使用编码转换函数将结果从 ISO-8859-1 转换为 UTF-8。不幸的是,我的 Ruby 不够好,无法告诉你如何做到这一点。
标签: ruby string encoding csv utf-8