如何在XSLT中基于子元素对父元素进行分组

huangapple go评论52阅读模式
英文:

How to group parent elements based on the child elements in XSLT

问题

我正在尝试根据具有相同值的子元素对多个元素进行分组。
具有相同值的每个Child1应该位于名为Group的节点内。请查看下面的期望输出。
以下是一个示例XML:

<?xml version="1.0" encoding="utf-8"?>
<Root>
    <Parent>
        <Child1>0123</Child1>
        <Child2>KIK</Child2>
        <Child3>YAM</Child3>
    </Parent>
    <Parent>
        <Child1>0123</Child1>
        <Child2>FIS</Child2>
        <Child3>BOL</Child3>
    </Parent>
    <Parent>
        <Child1>0123</Child1>
        <Child2>TOC</Child2>
        <Child3>INO</Child3>
    </Parent>
    <Parent>
        <Child1>456</Child1>
        <Child2>CHI</Child2>
        <Child3>KEN</Child3>
    </Parent>
    <Parent>
        <Child1>456</Child1>
        <Child2>ALA</Child2>
        <Child3>KING</Child3>
    </Parent>
</Root>

我希望输出如下所示:

<?xml version="1.0" encoding="utf-8"?>
<Root>
   <GROUP>  
        <Parent>
            <Child1>0123</Child1>
            <Child2>KIK</Child2>
            <Child3>YAM</Child3>
        </Parent>
        <Parent>
            <Child1>0123</Child1>
            <Child2>FIS</Child2>
            <Child3>BOL</Child3>
        </Parent>
        <Parent>
            <Child1>0123</Child1>
            <Child2>TOC</Child2>
            <Child3>INO</Child3>
        </Parent>
  </GROUP>  
  <GROUP>
        <Parent>
            <Child1>456</Child1>
            <Child2>CHI</Child2>
            <Child3>KEN</Child3>
        </Parent>
        <Parent>
            <Child1>456</Child1>
            <Child2>ALA</Child2>
            <Child3>KING</Child3>
        </Parent>
  </GROUP>  
</Root>

我只能复制整个代码,无法根据Child1上的值进行分组。

英文:

I am tring to group multiple elements based on the child element that has the same value.
Each Child1 that has the same value should be inside of a node called Group. See desired output below.
Here is a sample XML

`&lt;?xml version=&quot;1.0&quot; encoding=&quot;utf-8&quot;?&gt;
&lt;Root&gt;
    &lt;Parent&gt;
        &lt;Child1&gt;0123&lt;/Child1&gt;
        &lt;Child2&gt;KIK&lt;/Child2&gt;
        &lt;Child3&gt;YAM&lt;/Child3&gt;
    &lt;/Parent&gt;
    &lt;Parent&gt;
        &lt;Child1&gt;0123&lt;/Child1&gt;
        &lt;Child2&gt;FIS&lt;/Child2&gt;
        &lt;Child3&gt;BOL&lt;/Child3&gt;
    &lt;/Parent&gt;
    &lt;Parent&gt;
        &lt;Child1&gt;0123&lt;/Child1&gt;
        &lt;Child2&gt;TOC&lt;/Child2&gt;
        &lt;Child3&gt;INO&lt;/Child3&gt;
    &lt;/Parent&gt;
    &lt;Parent&gt;
        &lt;Child1&gt;456&lt;/Child1&gt;
        &lt;Child2&gt;CHI&lt;/Child2&gt;
        &lt;Child3&gt;KEN&lt;/Child3&gt;
    &lt;/Parent&gt;
    &lt;Parent&gt;
        &lt;Child1&gt;456&lt;/Child1&gt;
        &lt;Child2&gt;ALA&lt;/Child2&gt;
        &lt;Child3&gt;KING&lt;/Child3&gt;
    &lt;/Parent&gt;
&lt;/Root&gt;`

I want the output to be like the following:

`&lt;?xml version=&quot;1.0&quot; encoding=&quot;utf-8&quot;?&gt;
&lt;Root&gt;
   &lt;GROUP&gt;  
        &lt;Parent&gt;
            &lt;Child1&gt;0123&lt;/Child1&gt;
            &lt;Child2&gt;KIK&lt;/Child2&gt;
            &lt;Child3&gt;YAM&lt;/Child3&gt;
        &lt;/Parent&gt;
        &lt;Parent&gt;
            &lt;Child1&gt;0123&lt;/Child1&gt;
            &lt;Child2&gt;FIS&lt;/Child2&gt;
            &lt;Child3&gt;BOL&lt;/Child3&gt;
        &lt;/Parent&gt;
        &lt;Parent&gt;
            &lt;Child1&gt;0123&lt;/Child1&gt;
            &lt;Child2&gt;TOC&lt;/Child2&gt;
            &lt;Child3&gt;INO&lt;/Child3&gt;
        &lt;/Parent&gt;
  &lt;/GROUP&gt;  
  &lt;GROUP&gt;
        &lt;Parent&gt;
            &lt;Child1&gt;456&lt;/Child1&gt;
            &lt;Child2&gt;CHI&lt;/Child2&gt;
            &lt;Child3&gt;KEN&lt;/Child3&gt;
        &lt;/Parent&gt;
        &lt;Parent&gt;
            &lt;Child1&gt;456&lt;/Child1&gt;
            &lt;Child2&gt;ALA&lt;/Child2&gt;
            &lt;Child3&gt;KING&lt;/Child3&gt;
        &lt;/Parent&gt;
  &lt;/GROUP&gt;  
&lt;/Root&gt;`

I was only able to copy the whole code and not able to group it based on the values on Child1.

答案1

得分: 1

以下是翻译好的部分:

<xsl:stylesheet version="2.0" 
    xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
    <xsl:output method="xml" encoding="UTF-8" indent="yes"/>
    <xsl:strip-space elements="*"/>

    <xsl:template match="@*|node()">

        <xsl:copy>

            <xsl:apply-templates select="@*|node()" />

        </xsl:copy>

    </xsl:template>
    <xsl:template match="Root">
        <Root>
            <xsl:for-each-group select="Parent" group-by="Child1">

                <xsl:choose>
                    <xsl:when test="count(current-group()) gt 1">
                        <Group>
                            <xsl:apply-templates select="current-group()" />
                        </Group>
                    </xsl:when>
                    <xsl:otherwise>
                        <xsl:apply-templates select="current-group()" />
                    </xsl:otherwise>
                </xsl:choose>

            </xsl:for-each-group>
        </Root>
    </xsl:template>

</xsl:stylesheet>
英文:

Sharing my solution below:

&lt;xsl:stylesheet version=&quot;2.0&quot; 
    xmlns:xsl=&quot;http://www.w3.org/1999/XSL/Transform&quot;&gt;
    &lt;xsl:output method=&quot;xml&quot; encoding=&quot;UTF-8&quot; indent=&quot;yes&quot;/&gt;
    &lt;xsl:strip-space elements=&quot;*&quot;/&gt;
    
    
    &lt;xsl:template match=&quot;@*|node()&quot;&gt;
        
        &lt;xsl:copy&gt;
            
            &lt;xsl:apply-templates select=&quot;@*|node()&quot; /&gt;
            
        &lt;/xsl:copy&gt;
        
    &lt;/xsl:template&gt;
    &lt;xsl:template match=&quot;Root&quot;&gt;
        &lt;Root&gt;
            &lt;xsl:for-each-group select=&quot;Parent&quot; group-by=&quot;Child1&quot;&gt;
                
                &lt;xsl:choose&gt;
                    &lt;xsl:when test=&quot;count(current-group()) gt 1&quot;&gt;
                        &lt;Group&gt;
                            &lt;xsl:apply-templates select=&quot;current-group()&quot; /&gt;
                        &lt;/Group&gt;
                    &lt;/xsl:when&gt;
                    &lt;xsl:otherwise&gt;
                        &lt;xsl:apply-templates select=&quot;current-group()&quot; /&gt;
                    &lt;/xsl:otherwise&gt;
                &lt;/xsl:choose&gt;
                
            &lt;/xsl:for-each-group&gt;
        &lt;/Root&gt;
        
        
        
    &lt;/xsl:template&gt;

&lt;/xsl:stylesheet&gt;

huangapple
  • 本文由 发表于 2023年2月7日 03:54:01
  • 转载请务必保留本文链接:https://go.coder-hub.com/75365959.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定