我最近遇到了一个问题:我有两个XML文件,我需要检查它们是否与内容相同。两个文件都具有相同类型的元素节点,但顺序不同,并且节点的属性也相同。举个例子:
这是file1.xml
<Car name="Ferrari" speed="420">
<Engine>V12</Engine>
<Color name="Red"/>
</Car>
<Car name="Lamborghini" speed="380">
<Engine>SV</Engine>
<Color name="White"/>
</Car>
这是file2.xml
<Car speed="380" name="Lamborghini">
<Color name="White"/>
<Engine>SV</Engine>
</Car>
<Car speed="420" name="Ferrari">
<Color name="Red"/>
<Engine>V12</Engine>
</Car>
我需要比较这两个文件的东西,如果它们是“等于”则返回true,否则它会显示差异。 (在示例中,它必须返回true)
显然这是一个例子,我必须检查的文件里面有50.000+行元素。
我正在寻找的是一切:软件,使用的库,手动算法。
非常感谢。
答案 0 :(得分:1)
首先,我将您的样本包装到<R> ... </R>
以从中制作XML文档。
然后,我使用xsh将输入文件处理为元素的规范顺序:我按名称和@name属性对所有子元素进行了排序。
my $F1 := open file1.xml ;
my $F2 := open file2.xml ;
my $nodes = ( $F1//* | $F2//* ) ;
for my $element in { reverse @$nodes } {
if ($element/*) {
xmove &{ sort :k concat(name(), '|', @name) $element/* }
append $element ;
}
}
save :f file1.out.xml $F1 ;
save :f file2.out.xml $F2 ;
以相反的顺序走节点至关重要,否则排序将无法正常工作。
为了比较生成的XML,我使用了使用xmllint的旧xmldiff bash脚本:
#!/bin/bash
a=($@)
b=$#
f2=${a[$((--b))]}
f1=${a[$((--b))]}
diff "${a[@]:0:$b}" \
<(xmllint --c14n "$f1" |xmllint --format -) \
<(xmllint --c14n "$f2" |xmllint --format -)