0

このフラット XML では、指定された名前の会社の「直接の親」を取得するにはどうすればよいですか? Level = 0 で、特定の会社の前の最初の要素である要素を意味します。

したがって、会社名が VI であるとすると、会社 Z を取得する必要があります。

<Companies>
  <Company>
     <Name>X</Name>
     <Level>1</Level>
   </Company>
   <Company>
     <Name>Y</Name>
     <Level>1</Level>
   </Company>
   <Company>
     <Name>Z</Name>
     <Level>0</Level>
   </Company>
  <Company>
     <Name>V</Name>
     <Level>1</Level>
   </Company>
</Companies>

これは機能していませんか?

<xsl:value-of select="Companies/Company[Name='V']/preceding-sibling[Level=0]/last()
4

2 に答える 2

2

<xsl:value-of select="...">で、変更できます

Companies/Company[Name='V']/preceding-sibling[Level=0]/last()

(Companies/Company[Name='V']/preceding-sibling::*[Level=0])[last()]

ノート:

  • 先行兄弟軸は、他の軸と同様に::、ノード テスト ( など*) が続く必要があります。
  • last()ロケーションステップとして必要なものではありません(XSLT 2.0では合法かもしれませんが....よくわかりません)。代わりに、 predicate 内に入れます[ ]。述語[last()]は の省略形です[position() = last()]
  • 前にすべてに括弧を付け[last()]た理由は、@Lukasz がほのめかした理由ですpreceding-sibling::

したがって、preceding-sibling::*[last()]前の最後の兄弟を逆の順序で取得すると言うと、つまり、ドキュメントの順序で最初の前の兄弟が取得されます。実際には、ドキュメントの順序で最後のpreceding-sibling::*[1]前の兄弟が必要なので、@Lukasz のようにすることができます。または、私がしたことをすることができます(...)[last()]。どちらも有効です。以下で説明するように、私は後者を少し好みます。

この(...)[last()]形式が機能するのは、括弧によって、軸を持つステップだけではなく、その時点までのXPath 式全体[last()]に述語が適用されるためです。その結果、述語は、軸の逆方向によって制御されない式に適用されています。したがって、ドキュメントの順序で (指定されたセットの) 最後のノードを選択します。preceding-sibling::preceding-sibling::

括弧がないと、一部の XPath 式では、述語と軸の結合性に驚かされることがあります。優先順位規則について少し知っておく必要があります。確かに、私は優先順位規則の詳細を学ぶのが少し面倒です。しかし、(多くのプログラミング言語での) 私の経験では、構文解析の優先順位についてあまり目立たない規則に依存することは、コードをデバッグまたは変更しようとする次の人によってコードが誤解されたり、台無しにされたりすることを確実にするための良い方法です。(多くの場合、その「次の人」は 1 か月後の自分です。)

于 2012-10-16T14:35:03.020 に答える
1

次の XSLT フラグメントは、提供されたサンプル XML から前の Company 要素を取得します。

<xsl:copy-of select="Companies/Company[Name='V']/preceding-sibling::*[1]" />

それはそのようになります:

<Company>
    <Name>Z</Name>
    <Level>0</Level>
</Company>

ご覧のとおり、最初のノード ( *[1]) にアクセスしています。これは直感に反しているように見えるかもしれませんが、ここで詳細な説明を見つけることができます。

編集: Level=0 条件を考慮する必要があるかどうかわかりません。

于 2012-10-16T14:28:48.580 に答える