我有以下XML,需要有条件地过滤UnitOfMeasure是否有值。如果第一个UnitOfMeasure在哪里ID =' AcceptanceCriterionValue1'包含一个长度大于0的字符串,我应该选择该值。否则,我需要选择UnitOfMeasure节点值,其中ID =' AcceptanceCriterionValue2'。换句话说,如果pH1存在,抓住它。否则抓住pH2:
`
<MaterialLots>
<MaterialLotProperty>
<ID>AcceptanceCriterionValue1</ID>
<Value>
<ValueString>5</ValueString>
<UnitOfMeasure>pH1</UnitOfMeasure>
</Value>
</MaterialLotProperty>
<MaterialLotProperty>
<ID>AcceptanceCriterionValue2</ID>
<Value>
<ValueString>7</ValueString>
<UnitOfMeasure>pH2</UnitOfMeasure>
</Value>
</MaterialLotProperty>
</MaterialLots>
`
我需要执行以下逻辑。当pH1存在时,第一个xsl:when语句成功,但如果它为空,则xsl:否则会触发但由于某种原因没有返回pH2:
`
<xsl:choose>
<xsl:when test="ns:MaterialLots/ns:MaterialLotProperty/ns:ID='AcceptanceCriterionValue1' and string-length(ns:MaterialLots/ns:MaterialLotProperty/ns:Value/ns:UnitOfMeasure) > 0">
<xsl:value-of select="ns:MaterialLots/ns:MaterialLotProperty/ns:Value/ns:UnitOfMeasure" />
</xsl:when>
<xsl:otherwise>
<xsl:if test="ns:MaterialLots/ns:MaterialLotProperty/ns:ID='AcceptanceCriterionValue2' and string-length(ns:MaterialLots/ns:MaterialLotProperty/ns:Value/ns:UnitOfMeasure) > 0">
<xsl:value-of select="ns:MaterialLots/ns:MaterialLotProperty/ns:Value/ns:UnitOfMeasure" />
</xsl:if>
</xsl:otherwise>
</xsl:choose>
`
答案 0 :(得分:0)
测试你的第一个措施的表达是这个......
<xsl:when test="string-length(ns:MaterialLots/ns:MaterialLotProperty[ns:ID='AcceptanceCriterionValue1']/ns:Value/ns:UnitOfMeasure) > 0">
但是,使用变量可能稍微好一些,以避免重复。
<xsl:variable name="uom1" select="ns:MaterialLots/ns:MaterialLotProperty[ns:ID='AcceptanceCriterionValue1']/ns:Value/ns:UnitOfMeasure" />
<xsl:choose>
<xsl:when test="string-length($uom1) > 0">
<xsl:value-of select="$uom1" />
</xsl:when>
<xsl:otherwise>
<xsl:value-of select="ns:MaterialLots/ns:MaterialLotProperty[ns:ID='AcceptanceCriterionValue2']/ns:Value/ns:UnitOfMeasure" />
</xsl:otherwise>
</xsl:choose>
或者,您可以使用xsl:key
<xsl:key name="MLP" match="ns:UnitOfMeasure" use="../../ns:ID" />
然后你可以这样做
<xsl:choose>
<xsl:when test="string-length(key('MLP', 'AcceptanceCriterionValue1')) > 0">
<xsl:value-of select="key('MLP', 'AcceptanceCriterionValue1')" />
</xsl:when>
<xsl:otherwise>
<xsl:value-of select="key('MLP', 'AcceptanceCriterionValue2')" />
</xsl:otherwise>
</xsl:choose>
答案 1 :(得分:0)
您需要遍历每个MaterialLotProperty。 另外,在选择之前首先检查UnitOfMeasure的长度。
<?xml version="1.0"?>
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform" xmlns:ns="foo">
<xsl:output method="xml"/>
<xsl:template match="/">
<xml>
<xsl:for-each select='//ns:MaterialLotProperty'>
<xsl:if test='string-length(ns:Value/ns:UnitOfMeasure) > 0'>
<xsl:element name='output'>
<xsl:choose>
<xsl:when test="(ns:ID='AcceptanceCriterionValue1')">
<xsl:value-of select='ns:Value/ns:UnitOfMeasure'/>
</xsl:when>
<xsl:when test="(ns:ID='AcceptanceCriterionValue2')">
<xsl:value-of select='ns:Value/ns:UnitOfMeasure'/>
</xsl:when>
</xsl:choose>
</xsl:element>
</xsl:if>
</xsl:for-each>
</xml>
</xsl:template>
</xsl:stylesheet>
第二个XSL输出第一个非空白UnitOfMeasure。
<?xml version="1.0"?>
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform" xmlns:ns="foo">
<xsl:output method="xml"/>
<xsl:template match="/">
<xml>
<xsl:for-each select='//ns:MaterialLotProperty/ns:Value[string-length( ns:UnitOfMeasure ) > 0]/ns:UnitOfMeasure'>
<xsl:if test='(position() =1)'>
<xsl:element name='output'>
<xsl:value-of select='.'/>
</xsl:element>
</xsl:if>
</xsl:for-each>
</xml>
</xsl:template>
</xsl:stylesheet>
答案 2 :(得分:0)
我需要执行以下逻辑。第一个xsl:when语句 当pH1存在时成功,但如果它为空则xsl:否则会发射 但由于某种原因没有返回pH2
通常,在条件$n1
满足时选择节点$cond
并选择节点$n2
的XPath表达式是这样的:
$n1[$cond] | $n2[not($cond)]
在您的具体案例中,我们将$n1
替换为:
/*/MaterialLotProperty[ID='AcceptanceCriterionValue1']/Value/UnitOfMeasure
和$cond
:
text()
$n2
与:
/*/MaterialLotProperty[ID='AcceptanceCriterionValue2']/Value/UnitOfMeasure
因此,可以使用单个XPath表达式来选择所需节点:
/*/MaterialLotProperty[ID='AcceptanceCriterionValue1']/Value/UnitOfMeasure[text()]
|
/*/MaterialLotProperty[ID='AcceptanceCriterionValue2']/Value/UnitOfMeasure
[not(/*/MaterialLotProperty[ID='AcceptanceCriterionValue1']
/Value/UnitOfMeasure[text()])]
在此简单转换中使用此单个XPath表达式:
<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:value-of select=
"/*/MaterialLotProperty[ID='AcceptanceCriterionValue1']/Value/UnitOfMeasure[text()]
|
/*/MaterialLotProperty[ID='AcceptanceCriterionValue2']/Value/UnitOfMeasure
[not(/*/MaterialLotProperty[ID='AcceptanceCriterionValue1']
/Value/UnitOfMeasure[text()])]
"/>
</xsl:template>
</xsl:stylesheet>
在提供的XML文档上应用转换时:
<MaterialLots>
<MaterialLotProperty>
<ID>AcceptanceCriterionValue1</ID>
<Value>
<ValueString>5</ValueString>
<UnitOfMeasure>pH1</UnitOfMeasure>
</Value>
</MaterialLotProperty>
<MaterialLotProperty>
<ID>AcceptanceCriterionValue2</ID>
<Value>
<ValueString>7</ValueString>
<UnitOfMeasure>pH2</UnitOfMeasure>
</Value>
</MaterialLotProperty>
</MaterialLots>
产生了想要的正确结果:
pH1
如果您在XML文档中替换
<UnitOfMeasure>pH1</UnitOfMeasure>
使用:
<UnitOfMeasure/>
再次产生正确的结果:
pH2