具有度数符号的CSV的正确编码

时间:2014-05-09 05:00:18

标签: ruby csv encoding

我需要在标题内解析包含度数符号(°)的CSV文件。如果我尝试打开文件:

CSV.foreach('myfile.csv', headers: true) do |row|
  ...
end

我得到invalid byte sequence in UTF-8 (ArgumentError)。所以我尝试了其他一些编码(ISO-8859-1和ASCII-8BIT),但我总是遇到CSV::MalformedCSVError错误。

我应该指定哪种编码才能读取文件?

实际上我并不关心度数符号,所以它对我来说也是一个简单地忽略它的解决方案(并返回例如'Tx1 C'而不是'Tx1 °C')。

2 个答案:

答案 0 :(得分:1)

解析外部文件的默认编码是UTF-8(Encoding.default_external)。但是,CSV文件不以UTF-8格式存储。当Ruby尝试使用UTF-8编码解析非UTF-8编码的字节序列时,如果两个编码不兼容,则会出现错误。

您应首先获取CSV文件的实际编码。这可以通过在Notepad ++中打开CSV文件来确定,然后选中Encoding菜单下的选项。其他一些文本编辑器也有类似的功能,例如VIM,UltraEditor ......

假设您发现CSV文件的实际编码为GBK,请将代码重写为

CSV.foreach('myfile.csv', headers: true, encoding: 'GBK') do |row|
 ...
end

答案 1 :(得分:0)

你可以打开一个进程来删除小恶魔,然后再打开它:

system("LANG=C tr -d '\260' < myfile.csv >> $$.tmp && mv $$.tmp myfile.csv")

tr -d表示删除字符代码260,将结果保存到以进程ID($$)和扩展名.tmp命名的文件中。如果成功(&&),它将替换原始文件。

您可以在shell上单独尝试tr命令来测试它:

LANG=C tr -d '\260' < myfile.csv

如果您定位Windows,tr命令将无效,您可能必须执行以下操作才能删除第一行:

more +1 unhappy.csv > happy.csv

请注意,more的限制为65535行。