使用 Ruby/Nokogiri 从嵌套的 xml 文件中获取值
Get values from nested xml file with Ruby/Nokogiri
我正在尝试从以下 xml 文件中获取值,但我卡住了,因为我没有得到我想要的输出。可能有人可以帮我解决这个问题。
我当前的代码是:
require 'nokogiri'
doc = Nokogiri.XML(xml)
d=doc.xpath("//NtrkData/Rutins//GT_Nmbbrs/RngeDat")
puts d.xpath("//EE").text + "-" + d.xpath("//PR").text + "-" + d.xpath("//Brng").text + "-" + d.xpath("//Erng").text
我得到这个输出
3Z94PL-45156-73359-86353
但我想得到的是元素EE、PR、Brng(如果存在)和Erng(如果存在)的值。同一行中的所有 4 个值。
因此,对于以下 xml,我正在寻找的输出将是:
3Z9 45
4PL 156 73359 86353
xml是:
xml =<<_
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<main>
<Oganin>
<Oganna>EJ-MKKL</Oganna>
<CutryI>YUFG</CutryI>
<Ntwl>
<Ntrk>
<TGCo>KOLPWE</TGCo>
<NtrkType>Uymmls</NtrkType>
<NtrkData>
<Rutins>
<Rutinf>
<CTT>
<GT_Nmbbrs>
<RngeDat>
<Nmbbr>
<EE>3Z9</EE>
<PR>45</PR>
</Nmbbr>
</RngeDat>
<RngeDat>
<Nmbbr>
<EE>4PL</EE>
<PR>156</PR>
<Srng>
<Brng>73359</Brng>
<Erng>86353</Erng>
</Srng>
</Nmbbr>
</RngeDat>
</GT_Nmbbrs>
</CTT>
</Rutinf>
</Rutins>
</NtrkData>
</Ntrk>
</Ntwl>
</Oganin>
</main>
_
Nokogiri 有一个完美的文档,它清楚地指出 Nokogiri::XML::NodeSet#inner_text
没有做你期望的事情。相反,它 加入文本节点值 .
此外,没有办法像文档中建议的那样仅 map(&:text)
,因为您可能想保留 <Srng>
children 的所有物,这显然不可能批量查询。
也就是说,您需要查询各自的 parents 并迭代 children:
d.xpath('//Nmbbr').
map do |node|
[
node.xpath("./EE"),
node.xpath("./PR"),
node.xpath("./Srng").map do |node|
%w[Brng Erng].map { |path| node.xpath("./#{path}") }
end
]
end.
map { |nodes| nodes.flatten.map(&:text) }
#⇒ [["3Z9", "45"], ["4PL", "156", "73359", "86353"]]
现在迭代结果并根据需要打印它。
我正在尝试从以下 xml 文件中获取值,但我卡住了,因为我没有得到我想要的输出。可能有人可以帮我解决这个问题。
我当前的代码是:
require 'nokogiri'
doc = Nokogiri.XML(xml)
d=doc.xpath("//NtrkData/Rutins//GT_Nmbbrs/RngeDat")
puts d.xpath("//EE").text + "-" + d.xpath("//PR").text + "-" + d.xpath("//Brng").text + "-" + d.xpath("//Erng").text
我得到这个输出
3Z94PL-45156-73359-86353
但我想得到的是元素EE、PR、Brng(如果存在)和Erng(如果存在)的值。同一行中的所有 4 个值。
因此,对于以下 xml,我正在寻找的输出将是:
3Z9 45
4PL 156 73359 86353
xml是:
xml =<<_
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<main>
<Oganin>
<Oganna>EJ-MKKL</Oganna>
<CutryI>YUFG</CutryI>
<Ntwl>
<Ntrk>
<TGCo>KOLPWE</TGCo>
<NtrkType>Uymmls</NtrkType>
<NtrkData>
<Rutins>
<Rutinf>
<CTT>
<GT_Nmbbrs>
<RngeDat>
<Nmbbr>
<EE>3Z9</EE>
<PR>45</PR>
</Nmbbr>
</RngeDat>
<RngeDat>
<Nmbbr>
<EE>4PL</EE>
<PR>156</PR>
<Srng>
<Brng>73359</Brng>
<Erng>86353</Erng>
</Srng>
</Nmbbr>
</RngeDat>
</GT_Nmbbrs>
</CTT>
</Rutinf>
</Rutins>
</NtrkData>
</Ntrk>
</Ntwl>
</Oganin>
</main>
_
Nokogiri 有一个完美的文档,它清楚地指出 Nokogiri::XML::NodeSet#inner_text
没有做你期望的事情。相反,它 加入文本节点值 .
此外,没有办法像文档中建议的那样仅 map(&:text)
,因为您可能想保留 <Srng>
children 的所有物,这显然不可能批量查询。
也就是说,您需要查询各自的 parents 并迭代 children:
d.xpath('//Nmbbr').
map do |node|
[
node.xpath("./EE"),
node.xpath("./PR"),
node.xpath("./Srng").map do |node|
%w[Brng Erng].map { |path| node.xpath("./#{path}") }
end
]
end.
map { |nodes| nodes.flatten.map(&:text) }
#⇒ [["3Z9", "45"], ["4PL", "156", "73359", "86353"]]
现在迭代结果并根据需要打印它。