- PR -

XSLでXMLを要素の出現順に処理したい

1
投稿者投稿内容
rucio
ベテラン
会議室デビュー日: 2002/11/27
投稿数: 98
投稿日時: 2003-10-02 15:27
こんにちは。
XMLをXSLで加工してIEで表示しているのですが
要素ごとに処理することはできるのですが、要素の出現順に処理したいのです。
どんな方法があるかご教授ください。お願いします。

現在次のようになっています。
Test.xml-----------------------------------------
<?xml version="1.0" encoding="utf-8" ?>
<?xml-stylesheet type="text/xsl" href="Test.xsl"?>

<HISTORY>

<ERA>平安</ERA>
<PERSON>藤原道長</PERSON>
<PERSON>藤原頼道</PERSON>
<WAR>前九年の役</WAR>

<ERA>鎌倉</ERA>
<PERSON>源頼朝</PERSON>
<PERSON>北条時宗</PERSON>
<WAR>承久の乱</WAR>

</HISTORY>
-------------------------------------------------

Test.xsl-----------------------------------------
<?xml version="1.0" encoding="Shift-JIS"?>
<xsl:stylesheet xmlns:xsl="http://www.w3.org/TR/WD-xsl">

<xsl:template match="/">
<HTML>
<BODY>
<H1>歴史</H1>

<xsl:apply-templates select = "HISTORY/ERA" />
<xsl:apply-templates select = "HISTORY/PERSON" />
<xsl:apply-templates select = "HISTORY/WAR" />

</BODY>
</HTML>
</xsl:template>

<xsl:template match="ERA">
<H5>
<xsl:value-of select="." />時代
</H5><BR/>
</xsl:template>

<xsl:template match="PERSON">
<xsl:value-of select="." /><BR/>
</xsl:template>

<xsl:template match="WAR">
<FONT COLOR = "red">
<xsl:value-of select="." /><BR/>
</FONT>
</xsl:template>

</xsl:stylesheet>
-------------------------------------------------

結果---------------------------------------------
歴史
平安時代
鎌倉時代
藤原道長
藤原頼道
源頼朝
北条時宗
前九年の役
承久の乱
-------------------------------------------------

期待する結果--------------------------------------
歴史
平安時代
藤原道長
藤原頼道
前九年の役
鎌倉時代
源頼朝
北条時宗
承久の乱
--------------------------------------------------
TAKABE
常連さん
会議室デビュー日: 2003/05/14
投稿数: 43
投稿日時: 2003-10-02 18:11
XSLTの名前空間がWD版なのが気になりますが、そのことは置いておいて、ひとまず以下はいかがでしょうか。

<?xml version="1.0" encoding="UTF-8"?>
<xsl:stylesheet xmlns:xsl="http://www.w3.org/TR/WD-xsl">

<xsl:template match="/">
<HTML>
<BODY>
<H1>歴史</H1>
<xsl:apply-templates />
</BODY>
</HTML>
</xsl:template>

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

<xsl:template match="ERA">
<H5>
<xsl:value-of select="." />時代
</H5><BR/>
</xsl:template>

<xsl:template match="PERSON">
<xsl:value-of select="." /><BR/>
</xsl:template>

<xsl:template match="WAR">
<FONT COLOR = "red">
<xsl:value-of select="." /><BR/>
</FONT>
</xsl:template>

</xsl:stylesheet>
TAKABE
常連さん
会議室デビュー日: 2003/05/14
投稿数: 43
投稿日時: 2003-10-02 18:36
追伸です。
名前空間を正式なものに変え、またHISTORYのテンプレートを省略する方法もあります。
尚、H1の次にH5が来るなど、HTML的にもいろいろと不満がありますが(^^ このあたりはまた考えてみてくださいませ(^^

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

<xsl:template match="/">
<HTML>
<BODY>
<H1>歴史</H1>
<xsl:apply-templates />
</BODY>
</HTML>
</xsl:template>

<xsl:template match="ERA">
<H5>
<xsl:value-of select="." />時代
</H5><BR/>
</xsl:template>

<xsl:template match="PERSON">
<xsl:value-of select="." /><BR/>
</xsl:template>

<xsl:template match="WAR">
<FONT COLOR = "red">
<xsl:value-of select="." /><BR/>
</FONT>
</xsl:template>

</xsl:stylesheet>
t-wata
大ベテラン
会議室デビュー日: 2002/07/12
投稿数: 209
お住まい・勤務地: 東京
投稿日時: 2003-10-02 18:44
答えはTAKABEさんが書いているので良いとして、気になるのは、元のXML文書だと、
「平安時代の人物」をXML文書に現れる順番で表現している点です。
「平安時代の人物に特定のテンプレートを適用したい」とかが難しいですよね?
例えば、
<ERA name="平安">
<PERSON> ....</PERSON>
<WAR> ... </WAR>
</ERA>
のようにXMLを修正した方が良いと思います。
XSLTは、
<xsl:template match="ERA">
<H5>
<xsl:value-of select="@name" />時代
</H5><BR/>
<xsl:apply-templates select="PERSON"/>
<xsl:apply-templates select="WAR"/>
</xsl:template>
とすれば期待通りの出力になります。
rucio
ベテラン
会議室デビュー日: 2002/11/27
投稿数: 98
投稿日時: 2003-10-02 20:25
TAKABEさん、t-wataさんありがとうございます。
おかげで期待通りの結果が得られました。
お二人の指摘でXMLの幅も広がりました。

私にとっては
<xsl:apply-templates />
この書き方がポイントでした。
これがわかった時点ですっきりしました。

>名前空間を正式なものに変え、
昔、練習したときのサンプルを使いまわしていました。

>尚、H1の次にH5が来るなど、HTML的にもいろいろと不満がありますが(^^ このあたりはまた考えてみてくださいませ(^^
たしかに見にくいですね。
これでシンプル版が完成したので、これから見栄えをよくしていきたいと思います。

><ERA name="平安">
><PERSON> ....</PERSON>
><WAR> ... </WAR>
></ERA>
>のようにXMLを修正した方が良いと思います。
ご指摘ありがとうございます。
今回はXMLを吐き出す元プログラムがあって、そちらの方はいじれないのです。
この方法は別の機会に活用します。

どうもありがとうございました。

1

スキルアップ/キャリアアップ(JOB@IT)