我试图编写一个shell脚本,它将输入一组名称/值对和一个XML文件作为输入。
目的是在XML文件中搜索" name"来自名称/值对文件的字符串(用标签划分),并替换"值"在XML文件的同一级别定义的字符串(用标签划分)。
e.g。
名称/值对文件
trousers=blue
hat=red
shoes=brown
输入XML文件
<application>
<Pairs>
<Pair>
<name>trousers</name>
<value>black</value>
</Pair>
<IrritatingExtraLayer>
<Pair>
<name>hat</name>
<value>green</value>
</Pair>
</IrritatingExtraLayer>
<Pair>
<name>shirt</name>
<value>orange</value>
</Pair>
</Pairs>
</application>
预期的输出文件
<application>
<Pairs>
<Pair>
<name>trousers</name>
<value>blue</value>
</Pair>
<IrritatingExtraLayer>
<Pair>
<name>hat</name>
<value>red</value>
</Pair>
</IrritatingExtraLayer>
<Pair>
<name>shirt</name>
<value>orange</value>
</Pair>
</Pairs>
</application>
我已经创建了一个可以使用xmlstarlet执行此操作的脚本,但它非常慢(我使用的文件长达数千行)。我的脚本中的主代码片段(忽略预处理和后处理)是:
for line in ${namevaluepairs}; do
name=$(echo ${line} | cut -d'=' -f1)
value=$(echo ${line} | cut -d'=' -f2)
outputxml=$(echo ${outputxml} | xmlstarlet ed -u "//Pair/[name='${name}']/value" -v "${value}" )
done
我可以做些什么来改善这个?
答案 0 :(得分:1)
我通常使用xsh来完成类似的任务。我会对以下与xmlstarlet相比有多快感兴趣。
perl {
open $FH, '<', 'namevalues' or die $!;
while (<$FH>) {
chomp;
($n, $v) = split /=/;
$h->{$n} = $v;
}
} ;
open 1.xml ;
for //name {
$v = xsh:lookup('h', text()) ;
if $v set ../value $v ;
}
save :b ;
诀窍是将名称 - 值对存储在散列(map,dictionary)中,然后处理所有名称并从散列中检索相应的值。