1

私のシナリオでは、要素divののタグをチェックする必要があります。が存在する場合は、からのテキストをタグに挿入する必要があります。cdatabodydivnode2div

これは私の入力xmlです:

<?xml version="1.0" encoding="utf-8"?>
<root>
<node1>abc</node1>
<node2> needs to replace inside cdata div</node2>
<body> <![CDATA[
            <p>some text some textabcabcabcabc</p>

               <div class="marginBottom_4px">
               </div>
            <p>some text some textabcabc</P>

            ]]>
</body>
</root>

出力xmlは次のようになります。

<?xml version="1.0" encoding="utf-8"?>
<div class="marginBottom_10px">
abc
</div>
<div class="marginBottom_5px">

  <p>some text some textabcabcabcabc</p>

  <div class="marginBottom_4px">

   needs to replace inside cdata div
  </div>
  <p>some text some textabcabc</P>
</div>

私の変身は:

<?xml version="1.0" encoding="utf-8"?>
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
    xmlns:msxsl="urn:schemas-microsoft-com:xslt" exclude-result-prefixes="msxsl"
>
    <xsl:output method="xml" indent="yes"/>

  <xsl:template match="/">
    <xsl:value-of disable-output-escaping="yes" select ="$firstnode"/>
    <xsl:text disable-output-escaping="yes"><![CDATA[   <div class="marginBottom_10px">
   ]]>
  </xsl:text>
    <xsl:value-of disable-output-escaping ="yes" select="root/body"/>
    <xsl:text disable-output-escaping="yes"><![CDATA[
      </div>
     ]]>
    </xsl:text>
  </xsl:template>

  <xsl:variable name="firstnode">
    <xsl:text disable-output-escaping="yes"><![CDATA[
       <div class="marginBottom_10px">
     ]]>
     </xsl:text>
    <xsl:value-of disable-output-escaping ="yes" select="root/node1"/>
    <xsl:text disable-output-escaping="yes"><![CDATA[
      </div>
     ]]>
   </xsl:text>
  </xsl:variable>
</xsl:stylesheet>

出力を出すことができます。しかし、私のxmlは以下のように非常に複雑です。

<?xml version="1.0" encoding="utf-8" ?>
<ComplexXML>
  <environment>
   couple of nodes..
 </environment>
  <document>
    nodes
  </document>

<element cd="dsjdhfjk"  input="abc.xml" mode="" >
   <cd position="1">
     <attributes>
        <type>dummy text</type>
        <title>dummy text</title>
     </attributes>
  <content>
   <node2>
        <![CDATA[
          needs to replace inside cdata div
          ]]>
    </node2>
     <body>
        <![CDATA[
          <p>Lorem Ipsum is simply dummy text of the printing and typesetting industry. 
Lorem Ipsum has been the industry's standard dummy text ever since the 1500s,
 when an unknown printer took a galley of type and scrambled it to make a type 
specimen book </p>

             <div class="marginBottom_4px">
               </div>
               <p>Lorem Ipsum is simply dummy text of her including versions of Lorem Ipsum. </p>
           ]]>
      </body>
      <abt >
        <![CDATA[ 

               text from  abt node
               ]]>
      </abt>
    </content>
   </cd>
  </element>
</ComplexXML>

上記のxmlでは、abtノードを確認する必要があります。データがabtノードにある場合、出力は次のようになります。

 <?xml version="1.0" encoding="UTF-8"?>
      <div>
          text from  abt node

        <div class="marginBottom_5px"> 
                <p>Lorem Ipsum is simply dummy text of the printing and      typesetting              industry. 
Lorem Ipsum has been the industry's standard dummy text ever since the 1500s,
 when an unknown printer took a galley of type and scrambled it to make a type 
specimen book </p>

                   **<div class="marginBottom_4px">
                    </div>** I need to remove this div tag and place the node2 content here.

     <p>Lorem Ipsum is simply dummy text of her including versions of Lorem Ipsum. </p>

        </div>
</div>

ご迷惑をおかけして申し訳ありません。私はxsltを初めて使用します。学習段階にあります。ご案内いただけますか。

4

1 に答える 1

0

次の XSLT 1.0 スタイルシートは、出力例とコメントに基づいて、望ましい出力と思われるものを生成します。CDATA入力ドキュメントのテキストが整形式であることに依存し、以下を活用しdisable-output-escapingます。

<?xml version="1.0" encoding="utf-8"?>
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
    xmlns:msxsl="urn:schemas-microsoft-com:xslt" exclude-result-prefixes="msxsl"
    >
    <xsl:output method="xml" indent="yes"/>

    <xsl:template match="node1">
        <div class="marginBottom_10px">
            <xsl:apply-templates/>
        </div>
    </xsl:template>    

   <xsl:template match="node2" />     

   <xsl:template match="body">
       <div class="marginBottom_5px">
           <xsl:apply-templates/>
       </div>
   </xsl:template>

    <xsl:template match="body/text()[contains(.,'&lt;div') and contains(.,'&lt;/div>')]">
      <xsl:value-of 
          disable-output-escaping="yes" 
          select="substring-before(.,'&lt;/div')" />
      <xsl:value-of select="../../node2"/>  
      <xsl:value-of 
          disable-output-escaping="yes"
          select="substring-after(.,substring-before(.,'&lt;/div'))" /> 
   </xsl:template>
</xsl:stylesheet>

サンプル入力に対して適用すると、次のようになります。

<?xml version="1.0" encoding="UTF-8"?>
    <div class="marginBottom_10px">abc</div>

    <div class="marginBottom_5px"> 
            <p>some text some textabcabcabcabc</p>

               <div class="marginBottom_4px">
                needs to replace inside cdata div</div>
            <p>some text some textabcabc</P>


    </div>

注:出力は整形式ではありません。ドキュメント要素はありません。またはその他の包含要素<root>を作成するためのテンプレートを作成することをお勧めします。<div>


このバージョンは、他の入力形式を処理し、望ましい出力と思われるものを生成します。

<?xml version="1.0" encoding="utf-8"?>
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
    xmlns:msxsl="urn:schemas-microsoft-com:xslt" exclude-result-prefixes="msxsl"
    >
    <xsl:output method="xml" indent="yes"/>

    <!--rely on built-in templates, 
        which apply-templates to child nodes of elements
        and get value-of for text() -->

    <xsl:template match="content">
        <xsl:choose>
            <!-- if <abt> has a value, do the following -->
            <xsl:when test="normalize-space(abt)">
                <div>
                    <!-- apply templates to <abt>, 
                        built-in template will copy text to output-->
                    <xsl:apply-templates select="abt"/> 
                    <!-- apply templates to <body>, template defined below will handle it -->
                    <xsl:apply-templates select="body"/>
                </div>
            </xsl:when>
            <xsl:otherwise>
                <!--process child nodes -->
                <xsl:apply-templates />
            </xsl:otherwise>
        </xsl:choose>

    </xsl:template>

    <xsl:template match="node1">
        <div class="marginBottom_10px">
            <xsl:apply-templates/>
        </div>
    </xsl:template>    

    <!--empty template ensures that no content produced when templates applied to <node2>-->
    <xsl:template match="node2" />     

    <xsl:template match="body">
        <div class="marginBottom_5px">
            <xsl:apply-templates/>
        </div>
    </xsl:template>

    <!--Template for handling body/text() when <abt> does not have a value-->
    <xsl:template match="*[not(normalize-space(abt))]/body/text()[contains(.,'&lt;div') and contains(.,'&lt;/div>')]">
        <!--get the value of content preceding "</div"-->
        <xsl:value-of 
            disable-output-escaping="yes" 
            select="substring-before(.,'&lt;/div')" />
        <!--get the value of <node2> -->
        <xsl:value-of select="../../node2"/>  
        <!--get the value of content starting at "</div" -->
        <xsl:value-of 
            disable-output-escaping="yes"
            select="substring-after(.,substring-before(.,'&lt;/div'))" /> 
    </xsl:template>

    <!--Template for handling body/text() when <abt> does have a value -->
    <xsl:template match="*[normalize-space(abt)]/body/text()[contains(.,'&lt;div') and contains(.,'&lt;/div>')]">
        <!--get the value preceding "<div" -->
        <xsl:value-of 
            disable-output-escaping="yes" 
            select="substring-before(.,'&gt;div')" />
        <xsl:value-of select="../../node2"/>
        <!--get the value following "</div>" -->
        <xsl:value-of 
            disable-output-escaping="yes"
            select="substring-after(.,'&lt;/div>')" /> 
    </xsl:template>
</xsl:stylesheet>
于 2012-12-12T01:25:47.740 に答える