Итак, я пытаюсь разобрать файл с размером строки 400k +, используя Nokogiri.Разбор большого XML с Nokogiri
Файл XML имеет этот базовый формат:
<?xml version="1.0" encoding="windows-1252"?>
<JDBOR date="2013-09-01 04:12:31" version="1.0.20 [2012-12-14]" copyright="Orphanet (c) 2013">
<DisorderList count="6760">
*** Repeated Many Times ***
<Disorder id="17601">
<OrphaNumber>166024</OrphaNumber>
<Name lang="en">Multiple epiphyseal dysplasia, Al-Gazali type</Name>
<DisorderSignList count="18">
<DisorderSign>
<ClinicalSign id="2040">
<Name lang="en">Macrocephaly/macrocrania/megalocephaly/megacephaly</Name>
</ClinicalSign>
<SignFreq id="640">
<Name lang="en">Very frequent</Name>
</SignFreq>
</DisorderSign>
</Disorder>
*** Repeated Many Times ***
</DisorderList>
</JDBOR>
Вот код, который я создал, чтобы разобрать и вернуть каждый DisorderSign идентификатор и имя в базу данных:
require 'nokogiri'
sympFile = File.open("Temp.xml")
@doc = Nokogiri::XML(sympFile)
sympFile.close()
symptomsList = []
@doc.xpath("////DisorderSign").each do |x|
signId = x.at('ClinicalSign').attribute('id').text()
name = x.at('ClinicalSign').element_children().text()
symptomsList.push([signId, name])
end
symptomsList.each do |x|
Symptom.where(:name => x[1], :signid => Integer(x[0])).first_or_create
end
Это работает идеально на тестовых файлах, которые я использовал, хотя они были намного меньше, около 10000 строк.
Когда я пытаюсь запустить это на большом XML-файле, он просто не заканчивается. Я оставил его в одночасье, и это казалось просто блокировкой. Есть ли какая-то фундаментальная причина того, что код, который я написал, сделает эту память интенсивной или неэффективной? Я понимаю, что я храню все возможные пары в списке, но это не должно быть достаточно большим, чтобы заполнить память.
Благодарим за помощь.
Я не думаю, что '//// DisorderSign' делает то, что вы думаете, что он делает. –
Возможно, вам удастся получить дополнительную информацию, если вы обнаружите *, где * она блокируется. Это во время создания DOM (т. Е. Строки «Nokogiri :: XML»)? Вы всегда можете попробовать интерфейсы SAX или Reader. Это во время разбора? Попробуйте исправить «//// DisorderSign» в «// DisorderSign» или еще лучше использовать полный путь к DisorderSign и полностью избавиться от «//». –
У меня еще не было возможности проверить эти ответы, но я обязательно сделаю это, когда у меня появится такая возможность. Что касается вашего вопроса, я знаю, что он не блокируется во время создания DOM, через несколько секунд он проходит через это. Я попытаюсь использовать полный путь и отчитываться с любыми результатами, которые я получаю от этого, и с использованием ответов ниже. –