Это работа для мюнхенской группировки.Вы найдете многочисленные примеры этого в теге XSLT здесь, на StackOverflow.
Я полагаю, что вы говорите, что дочерние элементы уникально идентифицируются элементами e1, e2, e3 и e4 .Если два дочерних элемента имеют одинаковые элементы e , их следует объединить, чтобы был один дочерний со списком из нескольких mName и mValue элементов.
Сначала вам нужно определить ключ, чтобы помочь вам сгруппировать дочерние элементы
<xsl:key
name="children"
match="child"
use="concat(e1, concat('|', concat(e2, concat('|', concat(e3, concat('|', e4))))))"/>
Это создает ключ, который использует конкатенациюдочерние e элементы, которые можно использовать для поиска дочерних элементов.Обратите внимание на использование символа канала | для их объединения.Если какой-либо из ваших элементов может содержать символ конвейера, вам следует изменить его на использование другого символа.
Далее необходимо сопоставить все вхождения первого экземпляра каждого отдельного дочернего элемента * 1033.*.Это делается с помощью этого страшно выглядящего оператора
<xsl:apply-templates
select="
child[generate-id()
= generate-id(
key('children',
concat(e1, concat('|', concat(e2, concat('|', concat(e3, concat('|', e4))))))
)[1])]"/>
т.е. сопоставления child элементов, которые оказываются первым вхождением этого элемента в наш ключ.
Когда у вас естьсопоставив отдельные дочерние узлы, вы можете затем перебрать все другие дочерние узлы с одинаковыми e элементами
<xsl:for-each select="key('children', concat(e1, concat('|', concat(e2, concat('|', concat(e3, concat('|', e4)))))))">
Поместив это в целомдает
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:key name="children" match="child" use="concat(e1, concat('|', concat(e2, concat('|', concat(e3, concat('|', e4))))))"/>
<xsl:template match="/Parent">
<xsl:copy>
<xsl:apply-templates select="child[generate-id() = generate-id(key('children', concat(e1, concat('|', concat(e2, concat('|', concat(e3, concat('|', e4)))))))[1])]"/>
</xsl:copy>
</xsl:template>
<xsl:template match="child">
<xsl:copy>
<xsl:copy-of select="e1|e2|e3|e4" />
<xsl:for-each select="key('children', concat(e1, concat('|', concat(e2, concat('|', concat(e3, concat('|', e4)))))))">
<xsl:copy-of select="mName" />
<xsl:copy-of select="mValue" />
</xsl:for-each>
</xsl:copy>
</xsl:template>
</xsl:stylesheet>
Когда вы применяете это к вашему входному XML, он должен давать желаемый результат.