小时候的兄弟姐妹 [英] Sibling as Child

查看:31
本文介绍了小时候的兄弟姐妹的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

这是我要翻译的 xml.

Here is my xml that I want to translate.

<?xml version="1.0" encoding="UTF-8" ?>
<Loop xmlns="http://www.example.org">
  <Loop-2000A>
    <Element-628>81</Element-628>
    <Element-734 nil="nil82"/>
    <Element-735>83</Element-735>
    <Element-736>84</Element-736>
  </Loop-2000A>
  <Loop-2000B>
    <Element-1035>85</Element-1035>
    <Element-1036 nil="nil86"/>
    <Element-1037>87</Element-1037>
  </Loop-2000B>
  <Loop-2000B>
    <Element-1035>98</Element-1035>
    <Element-1036 nil="nil86"/>
    <Element-1037>97</Element-1037>
  </Loop-2000B>
  <Loop-2000C>
    <Element-1031>86</Element-1031>
    <Element-1039 nil="nil86"/>
    <Element-1038>25</Element-1038>
  </Loop-2000C>

  <Loop-2000A>
    <Element-628>89</Element-628>
    <Element-734 nil="nil82"/>
    <Element-735>99</Element-735>
    <Element-736>109</Element-736>
  </Loop-2000A>
  <Loop-2000B>
    <Element-1035>208</Element-1035>
    <Element-1036 nil="nil86"/>
    <Element-1037>87</Element-1037>

  </Loop-2000B>
  <Loop-2000C>
    <Element-1031>92</Element-1031>
    <Element-1039 nil="nil86"/>
    <Element-1038>90</Element-1038>
  </Loop-2000C>
  <Loop-2000B>
    <Element-1035>209</Element-1035>
    <Element-1036 nil="nil86"/>
    <Element-1037>97</Element-1037>
  </Loop-2000B>
</Loop>

要求是使 ...Loop-2000B 的 ...Loop-2000A 父代 ..和 2000-C 的 Loop-2000B 父代.Loop2000-C 在源 xml 中是可选的.Loop-2000A 之外的 xml 中的其他循环应按原样转换.因此,转换后的 XML 应如下所示.

The requirement is to make the ...Loop-2000A parents of ...Loop-2000B ..and Loop-2000B Parents of 2000-C . Loop2000-C is optional in source xml.Other Loop in xml which are outside Loop-2000A should be transformed as it is. Hence, the transformed XML should look something like this.

<?xml version = '1.0' encoding = 'UTF-8'?>
<ns2:TargetLoop xmlns:ns2="http://www.target.org"> 
  <Loop-2000A>
    <Loop-2000B>
      <Element-1035>85</Element-1035>
      <Element-1036 nil="nil86"/>
      <Element-1037>87</Element-1037>

    </Loop-2000B>
    <Loop-2000B>
      <Element-1035>98</Element-1035>
      <Element-1036 nil="nil86"/>
      <Element-1037>97</Element-1037>
      <Loop-2000C>
        <Element-1031>86</Element-1031>
        <Element-1039 nil="nil86"/>
        <Element-1038>25</Element-1038>
      </Loop-2000C>
    </Loop-2000B>
    <Element-628>81</Element-628>
    <Element-734 nil="nil82"/>
    <Element-735>83</Element-735>
    <Element-736>84</Element-736>
  </Loop-2000A>



  <Loop-2000A>
   <Loop-2000B>
      <Element-1035>208</Element-1035>
      <Element-1036 nil="nil86"/>
      <Element-1037>87</Element-1037>
      <Loop-2000C>
        <Element-1031>92</Element-1031>
        <Element-1039 nil="nil86"/>
        <Element-1038>90</Element-1038>
      </Loop-2000C>
    </Loop-2000B>
    <Loop-2000B>
      <Element-1035>209</Element-1035>
      <Element-1036 nil="nil86"/>
      <Element-1037>97</Element-1037>
    </Loop-2000B>
    <Element-628>89</Element-628>
    <Element-734 nil="nil82"/>
    <Element-735>99</Element-735>
    <Element-736>109</Element-736>
  </Loop-2000A>
</Loop>

任何建议将不胜感激

推荐答案

在 XSLT 2.0 中,您可能已经使用了 xsl:for-each-group,使用其 group-开始于 属性.但是,在 XSLT 1.0 中,这可以通过使用键来实现.您可以定义一个键来查找 Loop-2000B 元素的前一个 Loop-2000A 元素

In XSLT 2.0, you could have probably made use of xsl:for-each-group, using its group-starting-with attribute. In XSLT 1.0 though, this can be achieved by use of keys. You can define a key to look up the Loop-2000B elements by their first preceding Loop-2000A element

<xsl:key name="B" match="ex:Loop-2000B" use="generate-id(preceding-sibling::ex:Loop-2000A[1])" />

类似地,您可以通过它们前面的第一个 Loop-2000B 元素来关联 Loop-2000C 元素(尽管这可能没有必要,如果您说可以有每个 Loop-2000B

Similarlym you could do the same for associating Loop-2000C elements by their first preceding Loop-2000B element (Although this may not be necessary if you say there can be at most only one Loop-2000C element for each Loop-2000B

<xsl:key name="C" match="ex:Loop-2000C" use="generate-id(preceding-sibling::ex:Loop-2000B[1])" />

generate-id 函数是一个 XSLT 函数,可用于为每个节点生成唯一 id(如果它们现有的子元素之一可以唯一标识该元素,您也可以使用它).注意 ex: 前缀的使用是因为 XML 中的所有元素都在一个命名空间中,所以 XSLT 需要知道哪些命名空间元素在其中.

The generate-id function is an XSLT function that can be used to generate a unique id for each node (If one of their existing child elements could uniquely identify the element, you could also use that). Note the use of the ex: prefix is because all the elements in your XML are in a namespace, so XSLT needs to know which namespaces elements are in.

在您的 XSLT 中,您将首先选择 Loop-2000A 元素.

In your XSLT you would start off by selecting just the Loop-2000A elements.

<xsl:apply-templates select="ex:Loop-2000A" />

然后,在与 ex:Loop-2000A 匹配的模板中,您将使用键选择所有关联的 ex:Loop-2000B 元素

Then, within the template that matches ex:Loop-2000A you would select all the associated ex:Loop-2000B elements using the key

<xsl:apply-templates select="key('B', generate-id(current()))" />

您可以采用类似的方法在模板中获取与 ex:Loop-2000B 匹配的 ex:Loop-2000C.虽然,如果最多只有一个这样的 ex:Loop-2000C 元素,您可以这样做而不必担心在这种情况下的关键:

You would take a similar approach for getting the ex:Loop-2000C in the template that matches ex:Loop-2000B. Although, if there was ever only going to be at most one such ex:Loop-2000C element, you could do this and not worry about the key in this case:

<xsl:apply-templates select="following-sibling::*[1][self::ex:Loop-2000C]" />

这将获取紧随其后的同级元素,但前提是它是 Loop-2000C 元素.

This gets the very following sibling element, but only if it is a Loop-2000C element.

最后,其他现有元素可以通过身份转换进行匹配和复制

Finally, other existing elements can be matched and copied with the Identity Transform

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

试试这个 XSLT

<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform" 
     xmlns:ex="http://www.example.org">

  <xsl:output method="xml" omit-xml-declaration="yes" indent="yes" />
  <xsl:key name="B" match="ex:Loop-2000B" use="generate-id(preceding-sibling::ex:Loop-2000A[1])" />
  <xsl:key name="C" match="ex:Loop-2000C" use="generate-id(preceding-sibling::ex:Loop-2000B[1])" />

  <xsl:template match="*[ex:Loop-2000A]">
    <xsl:copy>
      <xsl:apply-templates select="@*"/>
      <xsl:apply-templates select="ex:Loop-2000A" />
      <xsl:apply-templates select="*[not(self::ex:Loop-2000A)][not(self::ex:Loop-2000B)][not(self::ex:Loop-2000C)]" />
    </xsl:copy>
  </xsl:template>

  <xsl:template match="ex:Loop-2000A">
    <xsl:copy>
      <xsl:apply-templates select="@*"/>
      <xsl:apply-templates select="key('B', generate-id(current()))" />
      <xsl:apply-templates />
    </xsl:copy>
  </xsl:template>

  <xsl:template match="ex:Loop-2000B">
    <xsl:copy>
      <xsl:apply-templates select="@*"/>
      <xsl:apply-templates select="key('C', generate-id(current()))" />
      <xsl:apply-templates />
    </xsl:copy>
  </xsl:template>

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

这篇关于小时候的兄弟姐妹的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆