groovy打印xml中元素的路径和值

时间:2016-01-10 21:58:49

标签: xml groovy xmlslurper gpath

我有以下xml:

<list>         
<cars>   
<model>2012</model>
<make>GM</make>         
</cars>    
</list>

我想将这些值打印为path:value,如下所示。

list/cars/model : 2012
list/cars/make : GM

我怎样才能做到这一点?我尝试了name()方法,但它只打印子项的名称。我想打印整个路径直到元素。

我只能使用xmlSlurper解析器来执行此操作。

感谢。

2 个答案:

答案 0 :(得分:1)

import groovy.util.XmlSlurper
import groovy.util.slurpersupport.NodeChild;
def rootNode = new XmlSlurper().parseText('<root><one a1="uno!"/><two>Some text!</two></root>' )

def printMap 
printMap = {node, path->
     if(node.getClass() == NodeChild){
        node.childNodes().each{
           printMap(it, (path ? path + "/" : "") + node.name())
        }
     } else {
        println "${path}/${node.name()}:${node.text()}"
     }
 }
 printMap(rootNode, "")

答案 1 :(得分:1)

def xml = '''
<list>         
    <cars>   
        <model>2012</model>
        <make>GM</make>
        <color>Gold</color>
    </cars>    
</list>
'''

def item = new XmlSlurper().parseText(xml)

item.'**'.inject([]) { acc, val ->
    def localText = val.localText()
    acc << val.name()

    if( localText ) {
        println "${acc.join('/')} : ${localText.join(',')}"
        acc = acc.dropRight(1) // or acc = acc[0..-2]
    } 
    acc
}

这将根据需要打印。上面是在树上使用depthFirst()搜索并使用inject(只是不改变任何其他列表)并查找localText()。如果遇到指示叶节点值的localText(),则打印路径和值。该路径已累积在用于注入的列表中。一个简单的join()将提供所需的格式。

以上已在Groovy 2.4.5中成功测试过。如果localText()中没有NodeChild,那么早于2.3.0的Groovy版本就是合理的,因为该方法自2.3.0以来已添加