在Ruby中解析制表符分隔文件的最佳方法是什么?

mbm*_*mbm 63 ruby tsv

在Ruby中解析制表符分隔文件的最佳(最有效)方法是什么?

jer*_*son 106

Ruby CSV库允许您指定字段分隔符.Ruby 1.9使用FasterCSV.像这样的东西会起作用:

require "csv"
parsed_file = CSV.read("path-to-file.csv", { :col_sep => "\t" })
Run Code Online (Sandbox Code Playgroud)

  • 请注意,如果任何制表符分隔值包含双引号,则此方法将失败.另一个答案中的StrictTsv建议更加健全. (9认同)
  • 另一种方法是使用`liberal_parsing`选项.`parsed_file = CSV.read("path-to-file.csv",{col_sep:"\ t",liberal_parsing:true)`来源[docs](https://ruby-doc.org/stdlib-2.5.1 /libdoc/csv/rdoc/CSV.html#method-c-new). (2认同)

mmm*_*ies 30

TSV的规则实际上与CSV略有不同.主要区别在于CSV具有在字段内粘贴逗号然后在字段内使用引号字符和转义引号的规定.我写了一个快速示例来说明简单响应如何失败:

require 'csv'
line = 'boogie\ttime\tis "now"'
begin
  line = CSV.parse_line(line, col_sep: "\t")
  puts "parsed correctly"
rescue CSV::MalformedCSVError
  puts "failed to parse line"
end

begin
  line = CSV.parse_line(line, col_sep: "\t", quote_char: "?")
  puts "parsed correctly with random quote char"
rescue CSV::MalformedCSVError
  puts "failed to parse line with random quote char"
end

#Output:
# failed to parse line
# parsed correctly with random quote char
Run Code Online (Sandbox Code Playgroud)

如果你想使用CSV库你可以使用一个随机引用字符,你不希望看到你的文件(示例显示这个),但你也可以使用更简单的方法,如下面显示的StrictTsv类来获得相同的效果,而不必担心现场报价.

# The main parse method is mostly borrowed from a tweet by @JEG2
class StrictTsv
  attr_reader :filepath
  def initialize(filepath)
    @filepath = filepath
  end

  def parse
    open(filepath) do |f|
      headers = f.gets.strip.split("\t")
      f.each do |line|
        fields = Hash[headers.zip(line.split("\t"))]
        yield fields
      end
    end
  end
end

# Example Usage
tsv = Vendor::StrictTsv.new("your_file.tsv")
tsv.parse do |row|
  puts row['named field']
end
Run Code Online (Sandbox Code Playgroud)

使用CSV库或更严格的选择取决于谁向您发送文件以及他们是否期望遵守严格的TSV标准.

有关TSV标准的详细信息,请访问http://en.wikipedia.org/wiki/Tab-separated_values

  • @JezenThomas感谢你的提醒.我内联所有代码示例以解决必须去看看要点的问题 (4认同)

mic*_*hau 6

实际上有两种不同类型的 TSV 文件。

  1. TSV 文件实际上是分隔符设置为 Tab 的 CSV 文件。例如,当您将 Excel 电子表格另存为“UTF-16 Unicode 文本”时,您会得到此信息。此类文件使用 CSV 引用规则,这意味着字段可以包含制表符和换行符,只要它们被引用即可,并且文字双引号会被写入两次。正确解析所有内容的最简单方法是使用csvgem:

    use 'csv'
    parsed = CSV.read("file.tsv", col_sep: "\t")
    
    Run Code Online (Sandbox Code Playgroud)
  2. 符合IANA 标准的 TSV 文件。不允许使用制表符和换行符作为字段值,并且不存在任何引用。例如,当您选择整个 Excel 电子表格并将其粘贴到文本文件中时,您会得到这样的结果(注意:如果某些单元格确实包含制表符或换行符,则会出现混乱)。可以使用简单的方法轻松地逐行解析此类 TSV 文件line.rstrip.split("\t", -1)(注意-1,这会阻止split删除空的尾随字段)。如果你想使用csvgem,只需quote_char设置nil

    use 'csv'
    parsed = CSV.read("file.tsv", col_sep: "\t", quote_char: nil)
    
    Run Code Online (Sandbox Code Playgroud)