我正在尝试按 XSLT 中的 2 个不同元素进行分组。首先通过 HOSTLOCID,然后通过 HOSTVENDORLOCID
I'm trying to group by 2 different elements in XSLT. First by HOSTLOCID, then by HOSTVENDORLOCID
下面是我根据之前对该组中其他问题的输入创建的 XSLT
<xsl:for-each-group select="/ns0:PurchaseOrders/ns0:PO" group-by="ns0:HOSTLOCID">
<tns:E1PORDCR1>
<xsl:for-each-group select="current-group()" group-by="ns0:HOSTVENDORLOCID">
<tns:E1BPMEPOHEADER>
<tns:COMP_CODE>
<xsl:value-of select="ns0:HOSTLOCID"/>
</tns:COMP_CODE>
<xsl:choose>
<xsl:when test="ns0:ORDERTYPEID = 1">
<tns:DOC_TYPE>NB</tns:DOC_TYPE>
</xsl:when>
<xsl:when test="ns0:ORDERTYPEID = 5">
<tns:DOC_TYPE>ZNB</tns:DOC_TYPE>
</xsl:when>
</xsl:choose>
<xsl:choose>
<xsl:when test="ns0:ORDERTYPEID = 1">
<tns:VENDOR>
<xsl:value-of select="ns0:HOSTVENDORLOCID"/>
</tns:VENDOR>
</xsl:when>
<xsl:when test="ns0:ORDERTYPEID = 5">
<tns:VENDOR>
<xsl:value-of select="ns0:HOSTREPLSOURCELOCID"/>
</tns:VENDOR>
</xsl:when>
</xsl:choose>
</tns:E1BPMEPOHEADER>
</xsl:for-each-group>
</tns:E1PORDCR1>
</xsl:for-each-group>
下面是我发送的输入
<PurchaseOrders>
<PO>
<HOSTLOCID>100-0001</HOSTLOCID>
<HOSTPARTID>100</HOSTPARTID>
<HOSTVENDORLOCID>IC100</HOSTVENDORLOCID>
</PO>
<PO>
<HOSTLOCID>100-0001</HOSTLOCID>
<HOSTPARTID>200</HOSTPARTID>
<HOSTVENDORLOCID>IC200</HOSTVENDORLOCID>
</PO>
<PO>
<HOSTLOCID>100-0001</HOSTLOCID>
<HOSTPARTID>300</HOSTPARTID>
<HOSTVENDORLOCID>IC100</HOSTVENDORLOCID>
</PO>
<PO>
<HOSTLOCID>100-0002</HOSTLOCID>
<HOSTPARTID>400</HOSTPARTID>
<HOSTVENDORLOCID>IC100</HOSTVENDORLOCID>
</PO> <PO>
<HOSTLOCID>100-0003</HOSTLOCID>
<HOSTPARTID>500</HOSTPARTID>
<HOSTVENDORLOCID>IC300</HOSTVENDORLOCID>
</PO>
<PO>
<HOSTLOCID>100-0002</HOSTLOCID>
<HOSTPARTID>600</HOSTPARTID>
<HOSTVENDORLOCID>IC100</HOSTVENDORLOCID>
</PO> <PO>
<HOSTLOCID>100-0001</HOSTLOCID>
<HOSTPARTID>700</HOSTPARTID>
<HOSTVENDORLOCID>IC100</HOSTVENDORLOCID>
</PO>
<PO>
<HOSTLOCID>100-0003</HOSTLOCID>
<HOSTPARTID>800</HOSTPARTID>
<HOSTVENDORLOCID>IC300</HOSTVENDORLOCID>
</PO>
</PurchaseOrders>
我想要的输出
<PO_Group>
<PurchaseOrders>
<!-- Group by Plant-Loc/Supplier -->
<PO>
<HOSTLOCID>100-0001</HOSTLOCID>
<HOSTPARTID>100</HOSTPARTID>
<HOSTVENDORLOCID>IC100</HOSTVENDORLOCID>
</PO>
<PO>
<HOSTLOCID>100-0001</HOSTLOCID>
<HOSTPARTID>300</HOSTPARTID>
<HOSTVENDORLOCID>IC100</HOSTVENDORLOCID>
</PO>
<PO>
<HOSTLOCID>100-0001</HOSTLOCID>
<HOSTPARTID>700</HOSTPARTID>
<HOSTVENDORLOCID>IC100</HOSTVENDORLOCID>
</PO>
</PurchaseOrders>
<PurchaseOrders>
<!-- Group by Plant-Loc/Supplier -->
<PO>
<HOSTLOCID>100-0002</HOSTLOCID>
<HOSTPARTID>400</HOSTPARTID>
<HOSTVENDORLOCID>IC100</HOSTVENDORLOCID>
</PO>
<PO>
<HOSTLOCID>100-0002</HOSTLOCID>
<HOSTPARTID>600</HOSTPARTID>
<HOSTVENDORLOCID>IC100</HOSTVENDORLOCID>
</PO>
</PurchaseOrders>
<PurchaseOrders>
<!-- Group by Plant-Loc/Supplier -->
<PO>
<HOSTLOCID>100-0003</HOSTLOCID>
<HOSTPARTID>500</HOSTPARTID>
<HOSTVENDORLOCID>IC300</HOSTVENDORLOCID>
</PO>
<PO>
<HOSTLOCID>100-0003</HOSTLOCID>
<HOSTPARTID>800</HOSTPARTID>
<HOSTVENDORLOCID>IC300</HOSTVENDORLOCID>
</PO>
</PurchaseOrders>
<PurchaseOrders >
<!-- Group by Plant-Loc/Supplier -->
<PO>
<HOSTLOCID>100-0001</HOSTLOCID>
<HOSTPARTID>200</HOSTPARTID>
<HOSTVENDORLOCID>IC200</HOSTVENDORLOCID>
</PO>
</PurchaseOrders>
<PO_Group>
我面临的问题是即使我能够对元素进行分组,所有元素都是其他元素正在被覆盖,因此我丢失了数据。对此有何建议?
谢谢
不清楚为什么要在 XSLT 中创建未在所需输出中显示的结果元素;也许您只需要简单地分组、包装和复制每个组即可,例如
<xsl:template match="/">
<PO_Group>
<xsl:for-each-group select="PurchaseOrders/PO" composite="yes" group-by="HOSTLOCID, HOSTVENDORLOCID">
<PurchaseOrders>
<xsl:apply-templates select="current-group()"/>
</PurchaseOrders>
</xsl:for-each-group>
</PO_Group>
</xsl:template>
这是带有 composite="yes"
的 XSLT 3(我认为自 Saxon 9.8 和 Altova XML 2017 R3 起支持),如果您坚持使用 XSLT 2 处理器,请使用例如
<xsl:template match="/">
<PO_Group>
<xsl:for-each-group select="PurchaseOrders/PO" group-by="concat(HOSTLOCID, '|', HOSTVENDORLOCID)">
<PurchaseOrders>
<xsl:apply-templates select="current-group()"/>
</PurchaseOrders>
</xsl:for-each-group>
</PO_Group>
</xsl:template>
下面是我根据之前对该组中其他问题的输入创建的 XSLT
<xsl:for-each-group select="/ns0:PurchaseOrders/ns0:PO" group-by="ns0:HOSTLOCID">
<tns:E1PORDCR1>
<xsl:for-each-group select="current-group()" group-by="ns0:HOSTVENDORLOCID">
<tns:E1BPMEPOHEADER>
<tns:COMP_CODE>
<xsl:value-of select="ns0:HOSTLOCID"/>
</tns:COMP_CODE>
<xsl:choose>
<xsl:when test="ns0:ORDERTYPEID = 1">
<tns:DOC_TYPE>NB</tns:DOC_TYPE>
</xsl:when>
<xsl:when test="ns0:ORDERTYPEID = 5">
<tns:DOC_TYPE>ZNB</tns:DOC_TYPE>
</xsl:when>
</xsl:choose>
<xsl:choose>
<xsl:when test="ns0:ORDERTYPEID = 1">
<tns:VENDOR>
<xsl:value-of select="ns0:HOSTVENDORLOCID"/>
</tns:VENDOR>
</xsl:when>
<xsl:when test="ns0:ORDERTYPEID = 5">
<tns:VENDOR>
<xsl:value-of select="ns0:HOSTREPLSOURCELOCID"/>
</tns:VENDOR>
</xsl:when>
</xsl:choose>
</tns:E1BPMEPOHEADER>
</xsl:for-each-group>
</tns:E1PORDCR1>
</xsl:for-each-group>
下面是我发送的输入
<PurchaseOrders>
<PO>
<HOSTLOCID>100-0001</HOSTLOCID>
<HOSTPARTID>100</HOSTPARTID>
<HOSTVENDORLOCID>IC100</HOSTVENDORLOCID>
</PO>
<PO>
<HOSTLOCID>100-0001</HOSTLOCID>
<HOSTPARTID>200</HOSTPARTID>
<HOSTVENDORLOCID>IC200</HOSTVENDORLOCID>
</PO>
<PO>
<HOSTLOCID>100-0001</HOSTLOCID>
<HOSTPARTID>300</HOSTPARTID>
<HOSTVENDORLOCID>IC100</HOSTVENDORLOCID>
</PO>
<PO>
<HOSTLOCID>100-0002</HOSTLOCID>
<HOSTPARTID>400</HOSTPARTID>
<HOSTVENDORLOCID>IC100</HOSTVENDORLOCID>
</PO> <PO>
<HOSTLOCID>100-0003</HOSTLOCID>
<HOSTPARTID>500</HOSTPARTID>
<HOSTVENDORLOCID>IC300</HOSTVENDORLOCID>
</PO>
<PO>
<HOSTLOCID>100-0002</HOSTLOCID>
<HOSTPARTID>600</HOSTPARTID>
<HOSTVENDORLOCID>IC100</HOSTVENDORLOCID>
</PO> <PO>
<HOSTLOCID>100-0001</HOSTLOCID>
<HOSTPARTID>700</HOSTPARTID>
<HOSTVENDORLOCID>IC100</HOSTVENDORLOCID>
</PO>
<PO>
<HOSTLOCID>100-0003</HOSTLOCID>
<HOSTPARTID>800</HOSTPARTID>
<HOSTVENDORLOCID>IC300</HOSTVENDORLOCID>
</PO>
</PurchaseOrders>
我想要的输出
<PO_Group>
<PurchaseOrders>
<!-- Group by Plant-Loc/Supplier -->
<PO>
<HOSTLOCID>100-0001</HOSTLOCID>
<HOSTPARTID>100</HOSTPARTID>
<HOSTVENDORLOCID>IC100</HOSTVENDORLOCID>
</PO>
<PO>
<HOSTLOCID>100-0001</HOSTLOCID>
<HOSTPARTID>300</HOSTPARTID>
<HOSTVENDORLOCID>IC100</HOSTVENDORLOCID>
</PO>
<PO>
<HOSTLOCID>100-0001</HOSTLOCID>
<HOSTPARTID>700</HOSTPARTID>
<HOSTVENDORLOCID>IC100</HOSTVENDORLOCID>
</PO>
</PurchaseOrders>
<PurchaseOrders>
<!-- Group by Plant-Loc/Supplier -->
<PO>
<HOSTLOCID>100-0002</HOSTLOCID>
<HOSTPARTID>400</HOSTPARTID>
<HOSTVENDORLOCID>IC100</HOSTVENDORLOCID>
</PO>
<PO>
<HOSTLOCID>100-0002</HOSTLOCID>
<HOSTPARTID>600</HOSTPARTID>
<HOSTVENDORLOCID>IC100</HOSTVENDORLOCID>
</PO>
</PurchaseOrders>
<PurchaseOrders>
<!-- Group by Plant-Loc/Supplier -->
<PO>
<HOSTLOCID>100-0003</HOSTLOCID>
<HOSTPARTID>500</HOSTPARTID>
<HOSTVENDORLOCID>IC300</HOSTVENDORLOCID>
</PO>
<PO>
<HOSTLOCID>100-0003</HOSTLOCID>
<HOSTPARTID>800</HOSTPARTID>
<HOSTVENDORLOCID>IC300</HOSTVENDORLOCID>
</PO>
</PurchaseOrders>
<PurchaseOrders >
<!-- Group by Plant-Loc/Supplier -->
<PO>
<HOSTLOCID>100-0001</HOSTLOCID>
<HOSTPARTID>200</HOSTPARTID>
<HOSTVENDORLOCID>IC200</HOSTVENDORLOCID>
</PO>
</PurchaseOrders>
<PO_Group>
我面临的问题是即使我能够对元素进行分组,所有元素都是其他元素正在被覆盖,因此我丢失了数据。对此有何建议?
谢谢
不清楚为什么要在 XSLT 中创建未在所需输出中显示的结果元素;也许您只需要简单地分组、包装和复制每个组即可,例如
<xsl:template match="/">
<PO_Group>
<xsl:for-each-group select="PurchaseOrders/PO" composite="yes" group-by="HOSTLOCID, HOSTVENDORLOCID">
<PurchaseOrders>
<xsl:apply-templates select="current-group()"/>
</PurchaseOrders>
</xsl:for-each-group>
</PO_Group>
</xsl:template>
这是带有 composite="yes"
的 XSLT 3(我认为自 Saxon 9.8 和 Altova XML 2017 R3 起支持),如果您坚持使用 XSLT 2 处理器,请使用例如
<xsl:template match="/">
<PO_Group>
<xsl:for-each-group select="PurchaseOrders/PO" group-by="concat(HOSTLOCID, '|', HOSTVENDORLOCID)">
<PurchaseOrders>
<xsl:apply-templates select="current-group()"/>
</PurchaseOrders>
</xsl:for-each-group>
</PO_Group>
</xsl:template>