2012-04-14 87 views
0

我有一个CSV,我喜欢保存所有我的散列值。我正在使用nokogiri sax解析xml文档,然后将其保存为CSV。Ruby:未定义的方法`<<'为零:NilClass

它解析并保存第一个XML文件,但开始解析第二个时,停下来,我得到的错误是这样的:

错误:NoMethodError: undefined method < <'的零:NilClass`

的零误差happing在@infodata [:标题] < < @content

SAX解析器:

require 'rubygems' 
require 'nokogiri' 
require 'csv' 

class MyDocument < Nokogiri::XML::SAX::Document 

    HEADERS = [ :titles, :identifier, :typeOfLevel, :typeOfResponsibleBody, 
       :type, :exact, :degree, :academic, :code, :text ] 

    def initialize 
    @infodata = {} 
    @infodata[:titles] = Array.new([]) 
    end 

    def start_element(name, attrs) 
    @attrs = attrs 
    @content = '' 
    end 
    def end_element(name) 
    if name == 'title' 
     Hash[@attrs]["xml:lang"] 
     @infodata[:titles] << @content 
     @content = nil 
    end 
    if name == 'identifier' 
     @infodata[:identifier] = @content 
     @content = nil 
    end 
    if name == 'typeOfLevel' 
     @infodata[:typeOfLevel] = @content 
     @content = nil 
    end 
    if name == 'typeOfResponsibleBody' 
     @infodata[:typeOfResponsibleBody] = @content 
     @content = nil 
    end 
    if name == 'type' 
     @infodata[:type] = @content 
     @content = nil 
    end 
    if name == 'exact'  
     @infodata[:exact] = @content 
     @content = nil 
    end 
    if name == 'degree' 
     @infodata[:degree] = @content 
     @content = nil 
    end 
    if name == 'academic' 
     @infodata[:academic] = @content 
     @content = nil 
    end 
    if name == 'code' 
     Hash[@attrs]['source="vhs"'] 
     @infodata[:code] = @content 
     @content = nil 
    end 
    if name == 'ct:text' 
     @infodata[:beskrivning] = @content 
     @content = nil 
    end 
    end 
    def characters(string) 
    @content << string if @content 
    end 
    def cdata_block(string) 
    characters(string) 
    end 
    def end_document 
    File.open("infodata.csv", "ab") do |f| 
     csv = CSV.generate_line(HEADERS.map {|h| @infodata[h] }) 
     csv << "\n" 
     f.write(csv) 
    end 
    end 
end 

创造新的每个文件是存储中的文件夹中的对象(47.000xml文件):

parser = Nokogiri::XML::SAX::Parser.new(MyDocument.new) 
counter = 0 

Dir.glob('/Users/macbookpro/Desktop/sax/info_xml/*.xml') do |item| 
    parser.parse(File.open(item, 'rb')) 
    counter += 1 
    puts "Writing file nr: #{counter}" 
end 

3 XML文件试图代码:https://gist.github.com/2378898 HTTPS:/ /gist.github.com/2378901 https://gist.github.com/2378904

+0

提示:而不是'csv = ...; csv <<“\ n”; f.write(csv)'只要'csv = ...; f.puts csv' – Phrogz 2012-04-15 00:43:26

+0

提示:'foo = Array.new([])'是荒谬的;只要做'foo = []'。 – Phrogz 2012-04-15 00:44:49

+0

提示:不要使用二进制模式的xml或csv – pguardiario 2012-04-15 05:42:39

回答

0

您正在做的是:

csv = CSV.generate_line(HEADERS.map {|h| @infodata[h] }) 
csv << "\n" 

如果由于某种原因,CSV.generate_line(HEADERS.map {|h| @infodata[h] })回报,你会尝试使用< <方法nil对象,这是没有定义的。

您可能需要添加一些条件以避免将“\ n”添加到csv如果为零。

+0

零误差在@infodata [:titles] << @content – SHUMAcupcake 2012-04-14 22:35:32

+0

@SHUMAcupcake嘿,那本来很高兴知道:p你在问题中包含更多细节,但仍然不够。错误_message_很好,但行号几乎同样重要。 – Phrogz 2012-04-15 00:42:50

相关问题