1

またしても問題のある作業です。私はあまり良くないxmlを持っています。たとえば、次のようになります。

<?xml version="1.0" encoding="UTF-8"?>
<Values>
<record name='svc_sig'>
<record name="sig_in">
    <array depth="1" name="rec_fields" type="record">
        <record>
            <!-- Some irrelevant metadata information with value node name... -->
            <value name="field_name">docTest</value>
            <value name="field_type">record</value>
            <value name="field_dim">0</value>
            <array depth="1" name="rec_fields" type="record">
                <record javaclass="com.wm.util.Values">
                    <!-- Some irrelevant metadata information with value node name... -->
                    <value name="field_name">doc.name</value>
                    <value name="field_type">string</value>
                    <value name="field_dim">0</value>
                </record>
            </array>
        </record>
        <record>
            <value name="field_name">docListTest</value>
            <value name="field_type">record</value>
            <value name="field_dim">1</value>
            <array depth="1" name="rec_fields" type="record">
                <record>
                    <value name="field_name">d0</value>
                    <value name="field_type">record</value>
                    <value name="field_dim">0</value>
                    <array depth="1" name="rec_fields" type="record">
                        <record>
                            <value name="field_name">d0.name</value>
                            <value name="field_type">string</value>
                            <value name="field_dim">0</value>
                        </record>
                    </array>
                </record>
            </array>
        </record>
        <record>
            <value name="field_name">packages_should_work</value>
            <value name="field_type">recref</value>
            <value name="field_dim">0</value>
            <value name="rec_ref">data:packages</value>
        </record>
        <record>
            <value name="field_name">packages_list_should_work</value>
            <value name="field_type">recref</value>
            <value name="field_dim">1</value>
            <value name="rec_ref">data:packages</value>
        </record>
    </array>
</record>
</record>
</Values>

簡単にするために、このxmlを既に指定されているJavaクラスにマップする必要があり、変更できません。それを念頭に置いて、この xml を意味のある名前の別の xml に変換する必要があります。例えば:

<sig_in>
   <record>
      <field_name>docTest</field_name>
      <field_type>record</field_type>
      <field_dim>0</field_dim>
   </record>
   <record>
      <field_name>docListTest</field_name>
      <field_type>record</field_type>
      <field_dim>1</field_dim>
   </record>
   <record>
      <field_name>packages_should_work</field_name>
      <field_type>recref</field_type>
      <field_dim>0</field_dim>
   </record>
   <record>
      <field_name>packages_list_should_work</field_name>
      <field_type>recref</field_type>
      <field_dim>1</field_dim>
   </record>
</sig_in>

これまでのところ、次のようなものを作成しました。

<?xml version="1.0" encoding="UTF-8"?>
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" version="1.0">
<xsl:output method="xml" indent="yes" encoding="UTF-8" />
    <xsl:template match="/" name="service_signature">
        <sig_in>
            <xsl:for-each select="Values/record[@name='svc_sig']/record[@name='sig_in']/array[@name]/record">
                <record>
                    <field_name><xsl:value-of select="value[@name='field_name']/text()"/></field_name>
                    <field_type><xsl:value-of select="value[@name='field_type']/text()"/></field_type>
                    <field_dim><xsl:value-of select="value[@name='field_dim']/text()"/></field_dim>
                </record>
            </xsl:for-each>
        </sig_in>
    </xsl:template>

</xsl:stylesheet>

主な要素では機能しますが、ネストされたレコードでは機能しません。xsl:for-each を作成し、タイプがレコードの場合は各アイテムを反復処理できますが、それではあまり解決しません。どんなに深くてもいいから。再帰を使用する必要があることはわかっていますが、この特定のケースでどのようにそれを行うことができるか想像できません。

@Edit - ネストされた型の修正:

<record>
  <field_name>docListTree</field_name>
  <field_type>record</field_type>
  <field_dim>1</field_dim>
  <record>
    <field_name>d0</field_name>
    <field_type>record</field_type>
    <field_dim>0</field_dim>
    <record>
      <field_name>d0.name</field_name>
      <field_type>string</field_type>
      <field_dim>0</field_dim>
    </record>
  </record>
</record>

元の型がネストされている場所がわかるように、結果の xml でも同じものが必要です。または、フラットでは、親ノードと子ノードに一意の識別子が必要になるため、どれがどれを含むかがわかります。とにかく構造を崩してはいけません。

@編集: - スペースを節約したかったので、壁の背後にある複雑さを示すことができなかったことを本当に申し訳ありません。したがって、すべてのレコードには値名ノードが含まれます。それらのほとんどには、私が必要としない役に立たないメタデータ情報しか含まれていません。また、@name {sig_in, sig_out} を持つ 2 つのレコードがあり、そこから sig_in のみが必要であり、field_name、field_type、field_dim 情報、および同じようにネストされたレコードがあります。推奨されるすべてのオプションに目を通し、ニーズに合わせてそれらを変更しようとします。

いつも助けてくれてありがとう!- ジョー

4

3 に答える 3

0

この XSLT は、投稿された結果を生成できます。

<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" version="1.0">
  <xsl:output method="xml" indent="yes" encoding="UTF-8" />
  <xsl:template match="/" name="service_signature">
    <sig_in>
      <xsl:for-each select="/record[@name='sig_in']/array[@name]/record">
        <record>
          <field_name><xsl:value-of select="value[@name='field_name']/text()"/></field_name>
          <field_type><xsl:value-of select="value[@name='field_type']/text()"/></field_type>
          <field_dim><xsl:value-of select="value[@name='field_dim']/text()"/></field_dim>
        </record>
      </xsl:for-each>
    </sig_in>
  </xsl:template>

</xsl:stylesheet>

ただし、すべてのレコードを反復処理する場合は、次のようにします。

<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" version="1.0">
  <xsl:output method="xml" indent="yes" encoding="UTF-8" />
  <xsl:template match="/" name="service_signature">
    <sig_in>
      <xsl:for-each select="//array[@name]/record">
        <record>
          <field_name><xsl:value-of select="value[@name='field_name']/text()"/></field_name>
          <field_type><xsl:value-of select="value[@name='field_type']/text()"/></field_type>
          <field_dim><xsl:value-of select="value[@name='field_dim']/text()"/></field_dim>
        </record>
      </xsl:for-each>
    </sig_in>
  </xsl:template>

</xsl:stylesheet>
于 2013-05-07T07:30:25.070 に答える
0

次のようなことを試してください:

<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
    <xsl:output indent="yes"/>

    <xsl:template match="value[@name]">
        <xsl:element name="{@name}">
            <xsl:value-of select="text()"/>
        </xsl:element>

    </xsl:template>

    <xsl:template match="record">
            <xsl:copy>
                <xsl:apply-templates  />
            </xsl:copy>
    </xsl:template>
     <xsl:template match="/*">
        <xsl:apply-templates  />
    </xsl:template>

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

次の出力が生成されます。

<?xml version="1.0"?>
<record>
  <field_name>docTest</field_name>
  <field_type>record</field_type>
  <field_dim>0</field_dim>
  <record>
    <field_name>doc.name</field_name>
    <field_type>string</field_type>
    <field_dim>0</field_dim>
  </record>
</record><record>
  <field_name>docListTest</field_name>
  <field_type>record</field_type>
  <field_dim>1</field_dim>
  <record>
    <field_name>d0</field_name>
    <field_type>record</field_type>
    <field_dim>0</field_dim>
    <record>
      <field_name>d0.name</field_name>
      <field_type>string</field_type>
      <field_dim>0</field_dim>
    </record>
  </record>
</record><record>
  <field_name>packages_should_work</field_name>
  <field_type>recref</field_type>
  <field_dim>0</field_dim>
  <rec_ref>data:packages</rec_ref>
</record><record>
  <field_name>packages_list_should_work</field_name>
  <field_type>recref</field_type>
  <field_dim>1</field_dim>
  <rec_ref>data:packages</rec_ref>
</record>

問題の詳細情報を更新します。

レコードまたは値のテンプレートに条件を簡単に入れることができます。これは私が理解したことです:@name値を持つレコードを持つレコードのみを考慮してください: "sig_in".
これを試して:

?xml version="1.0" encoding="utf-8"?>
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
    <xsl:output indent="yes"/>

    <xsl:template match="value[@name = 'field_name' or
                            @name = 'field_type' or
                            @name = 'field_dim']">
        <xsl:element name="{@name}">
            <xsl:value-of select="text()"/>
        </xsl:element>

    </xsl:template>

    <xsl:template match="record[descendant-or-self::record[@name='sig_in'] or 
                  ancestor::record[@name='sig_in']]">
            <xsl:copy>
                <xsl:apply-templates  />
            </xsl:copy>
    </xsl:template>


    <xsl:template match="/*">
        <xsl:apply-templates  />
    </xsl:template>

    <xsl:template match="node()">
        <xsl:apply-templates select="node()" />
    </xsl:template>
</xsl:stylesheet>
于 2013-05-07T08:06:42.433 に答える