Вам не нужно использовать какие-либо xsl:for-each
для решения проблемы, гораздо больше вам не нужно вложенные xsl:for-each
.
На самом деле,требуемые ItemA
элементы могут быть выбраны с помощью одного выражения XPath :
/*/ItemA[AName = 'BBC'
and
not(ANum = /*/ItemB/tempBNum)
]
Поэтому простое преобразование XSLT, которое оценивает вышеприведенное выражение XPath и копирует результат в вывод:1014 *
Когда это преобразование применяется к предоставленному XML-документу :
<myData>
<ItemA>
<ANum>0213</ANum>
<AName>OOC</AName>
</ItemA>
<ItemA>
<ANum>0031</ANum>
<AName>BBC</AName>
</ItemA>
<ItemA>
<ANum>0214</ANum>
<AName>BBC</AName>
</ItemA>
<ItemA>
<ANum>0044</ANum>
<AName>BBC</AName>
</ItemA>
<ItemB>
<tempBNum>0031</tempBNum>
</ItemB>
<ItemB>
<tempBNum>0044</tempBNum>
</ItemB>
</myData>
желаемый, правильный результат получается :
<ItemA>
<ANum>0214</ANum>
<AName>BBC</AName>
</ItemA>
Если нам нужны только значения текстовых узлов, просто используйте функцию string()
:
string(/*/ItemA[AName = 'BBC' and not(ANum = /*/ItemB/tempBNum)])
Затем измененное преобразование:
<xsl:stylesheet version="1.0"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:output omit-xml-declaration="yes" indent="yes"/>
<xsl:template match="/">
<xsl:copy-of select=
"string(/*/ItemA[AName = 'BBC' and not(ANum = /*/ItemB/tempBNum)])"/>
</xsl:template>
</xsl:stylesheet>
при применении ктот же XML-документ (см. выше) создает:
0214
BBC
Примечание : Если производительность начинает иметь значение, использование ключей может быть следующим шагом для повышения эффективности преобразования.