0

私はしばらくこれに取り組んできましたが、どのような種類の実用的な解決策にもたどり着くことができませんでした。これはすべて xml バージョン 1 にあります。

dog_info.xml と呼ばれる最初のファイルには、次のようなものが含まれています。

<?xml version"1.0" encoding="UTF-8"?>
<dog_info version="2" dog_num="2" update_time="2013-15-05T14:80:00Z">
   <dog_list xml: lang="en">
      <dog id="1" name="Nikki" desc="Black with brown spots"/>
      <dog id="2" name="Zulu" desc="Oreo color"/>
      <dog id="3" name="Tyler" desc="brown dog"/>
      <dog id="4" name="Sally" desc="milk color"/>
      <dog id="5" name="Joe" desc="brown and grey color"/>
   </dog_list>
   <dog_list xml:lang="piggylatin">
      <dog id="1" name="Nikky" desc="black spots with black and brown spots"/>
      <dog id="2" name="apples" desc="green, red or blue apples"/>
      <dog id="3" name="Taylor" desc="yellow dog"/>
      <dog id="4" name="Susan" desc="a dog"/>
      <dog id="5" name="Jason" desc="a cat"/>
   </dog_list>
</dog_info>

profile.xml と呼ばれる 2 番目のファイルには、次のようなものがあります。

<?xml version="1.0" encoding="UTF-8"?>
<profile>
   <animal-helper>
      <animal>
         <category>
            <rule>
               <value>1</value>
               <deny />
            </rule>
            <rule>
               <value>2</value>
               <deny />
            </rule>
         </category>
      </animal>
   </animal-helper>
</profile>

3番目のファイルは私が書いているものですが、行き詰まっています。情報を表示するために html に解析できる xsl である必要があります。

profile.xml の値は 1 で、deny です。拒否の場合は、dog_list.xml の id と照合され、名前と説明が取得されます。他の拒否と同じです。

<allow />タグはありませんが、 <deny />. したがって、dog_list.xml の残りの ID はすべて許可されます。HTMLの独自のカテゴリにリストする必要があります。

また、言語が「piggylatin」または「en」でない場合、デフォルトで「en」になることにも注意する必要があります。どんな助けでも大歓迎です。

編集:

実際のファイルは非常に大きく、作業に使用されます。そのため、機能させるために必要なものに似たものを再作成する必要がありました。

私は次のようなものを持っています:

...


<xsl:for-each select="$HELPER/animal/category/rule[name=false()]">
   <xsl:variable name="currentValue" select="value/text()"/>
   <xsl:variable name="dogValue" select="$DOG_LIST"/> 
   <xsl:for-each select="$dogValue/dog[@id = $currentValue]">
      <xsl:apply-templates/><xsl:if test="position() != last()"><xsl:text disable-output-escaping="yes"><![CDATA[<br />]]></xsl:text></xsl:if>
   </xsl:for-each>
</xsl:for-each>
...

編集2:

上記のコードのスニペットは、html テーブル (拒否セクション) の一部です。次のようになります。

「否定」
ニッキー・
ズールー

「許可された」
タイラー
・サリー
・ジョー

したがって、"Deny" は値 1 と 2 を見つけ、id 1 と 2 に一致し、名前を返します。そして、「許可」は、ID 3、4、5 (1 と 2 のため) を検出し、拒否され、名前を返します。

この要素の目的は<deny />、拒否された犬を選択してリストすることです。次に、それに基づいて、拒否されなかった他の「id」が許可されます。

私が書いたコードの上記の部分には、2 つの部分があります。「拒否」部分と「許可」部分。許可された部分は、最初に選択されなかった他の「ID」をテストする必要があります<deny />

4

2 に答える 2

2

まず第一に、<xsl:for-each>存在することを忘れてください。それは簡単なことを難しくします。そして、あなたは(ほとんど)それを必要としません。

ネストされたループを記述する代わりに、テンプレートを記述してテンプレート マッチングを使用し、ノードの選択それらへのテンプレートの適用に集中します。

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

  <xsl:variable name="profile" select="document('profile.xml')" />
  <xsl:variable name="denied" select="$profile//animal/category/rule[deny]/value" />

  <xsl:template match="/*">
    <html>
      <head><!-- ... --></head>
      <body>
        <h1>Denied</h1>
        <ul>
          <xsl:apply-templates select="dog_list/dog[@id = $denied]" />
        </ul>

        <h1>Allowed</h1>
        <ul>
          <xsl:apply-templates select="dog_list/dog[not(@id = $denied)]" />
        </ul>
      </body>
    </html>
  </xsl:template>

  <xsl:template match="dog">
    <li><xsl:value-of select="@name" /></li>
  </xsl:template>
</xsl:stylesheet>

言語とデフォルト言語に関しては、パラメーターとキーを操作します。

<xsl:param name="defaultLang" select="'en'" />
<xsl:param name="displayLang" select="'piggylatin'" />

<!-- index dogs by their language and ID -->
<xsl:key name="kDogByLang" match="dog" select="concat(../@xml:lang, '/', @id)" />


<!-- ...and replace the dog template with this: -->

<xsl:template match="dog">
  <xsl:variable name="default" select="key('kDogByLang', concat($defaultLang, '/', @id))" />
  <xsl:variable name="display" select="key('kDogByLang', concat($displayLang, '/', @id))" />

  <xsl:choose>
    <!-- if this is the correct language, output it -->
    <xsl:when test="generate-id() = generate-id($display)">
      <li><xsl:value-of select="$display/@name" /></li>
    </xsl:when>

    <!-- if this is the default lang (and no correct lang exists), output this -->
    <xsl:when test="generate-id() = generate-id($default) and not($display)">
      <li><xsl:value-of select="$default/@name" /></li>
    </xsl:when>

    <!-- there is no "otherwise" - all other cases shall not produce output -->
  </xsl:choose>
</xsl:template>

このようにして、正しいパラメーター値を渡すことで、スタイルシートの出力を簡単に構成できます。

サンプル: http://www.xmlplayground.com/jv3TvQ

于 2013-10-27T09:55:48.273 に答える
2

ルール要素をループする代わりに、ロジックを逆にして最初のファイルのdog要素をループし、最初に対応するdenyを持つものだけを選択し、次にそうでないものを選択することができます。

ルール要素の外観を作成するには、次のように変数を定義できます。

<xsl:variable name="lookup" select="document('profile.xml')/profile/animal-helper/animal/category/rule" />

拒否されたdog要素を検索するには、これを行うだけです (最初のファイルのdog_info要素に配置されていると仮定します)。

<xsl:apply-templates select="dog[@id=$lookup[deny]/value]" />

そして、否定されていないものを取得するには、これを行うだけです

<xsl:apply-templates select="dog[not(@id=$lookup[deny]/value)]" />

「言語」に関しては、必要な言語でdog_info要素を選択することから始めることができます

<xsl:apply-templates select="dog_list[@xml:lang='en']" />

このXSLTを試してください

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

   <xsl:variable name="lookup" select="document('profile.xml')/profile/animal-helper/animal/category/rule" />

   <xsl:template match="/*">
      <xsl:apply-templates select="dog_list[@xml:lang='en']" />
   </xsl:template>

   <xsl:template match="dog_list">
      DENY:<br />
         <xsl:apply-templates select="dog[@id=$lookup[deny]/value]" />
      APPROVE:<br />
         <xsl:apply-templates select="dog[not(@id=$lookup[deny]/value)]" />
    </xsl:template>

     <xsl:template match="dog">
         <xsl:value-of select="@name" />
         <br />
   </xsl:template>
</xsl:stylesheet>

これにより、次のように出力されます

  DENY:<br>
  Nikki<br>
  Zulu<br>
  APPROVE:<br>
  Tyler<br>
  Sally<br>
  Joe<br>
于 2013-10-27T09:26:06.693 に答える