xslt(表)通过匹配属性值

时间:2010-03-14 13:25:48

标签: xml xslt xpath

我需要为下面的xml生成一个xsl表,用于属性fname和lname。我想我在xpath中做错了什么。有人可以通过为下面的xml写一个xsl表来帮助我。

<sparql>
    <head>
        <variable name="s"/>
        <variable name="fname"/>
        <variable name="lname"/>
    </head>
    <results>
        <result>
            <binding name="s">
                <uri>http://tn.gov.in/Person/41</uri>
            </binding>
            <binding name="fname">
                <literal>G</literal>
            </binding>
            <binding name="lname">
                <literal>Vn</literal>
            </binding>
        </result>
        <!-- more result elements -->
    </results>
</sparql>
像我有一个查询语义数据的servlet,使用jena ... servlet的输出在xml之上......设置输出格式时Jena有一个选项,可以在其中设置XML的样式来映射xsl文件..

现在,当我使用lachlan的例子时,我得到了输出,因为我在该评论中发布了.. 没有,我的输出必须是表格的形式,其中应显示fname,lname

fname             lname
------------------------
M           v
G         v

等...

我必须做的错误是什么? 这是我的xsl:

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

    <xsl:template match="sparql/results">
        <html>
            <head><title>persons</title>
            </head>
            <body>
                <table width="40%" border="1">
                    <THEAD>
                        <TR>
                            <TD><B>first name</B></TD>
                            <TD><B>last name</B></TD>
                        </TR>
                    </THEAD> 
                    <TBODY>
                        <xsl:for-each select="result">
                            <TR>    
                                <TD><xsl:value-of select="binding[@name='fname']/literal/text()" /></TD>     
                                <TD><xsl:value-of select="binding[@name='fname']/literal/text()" /></TD> 

                            </TR>
                        </xsl:for-each>
                    </TBODY>
                </table>
            </body>
        </html>
    </xsl:template>

</xsl:stylesheet>

我的输出是:

http://tn.gov.in/Person/41 Gn http://tn.gov.in/Person/43 Vn http://tn.gov.in/Person/37 Mn http://tn.gov.in/Person/39 Vn

我在xsl def中输入了名称='s'但是我在输出中也得到了那些格式不像表格的那样..

是的,我有root sparql的nampespace ..

<sparql xmlns="http://www.w3.org/2005/sparql-results#">
  <head>
    <variable name="s"/>
    <variable name="fname"/>
    <variable name="lname"/>
    <variable name="title"/>
    <variable name="mno"/>
    <variable name="community"/>

  </head>
  <results>
    <result>
      <binding name="s">
        <uri>http://tn.gov.in/Person/45</uri>
      </binding>
      <binding name="fname">
        <literal>/literal>

      </binding>
      <binding name="lname">
        <literal>K</literal>
      </binding>
      <binding name="title">
        <literal>Mr.</literal>
      </binding>
      <binding name="mno">

        <literal>876876</literal>
      </binding>
      <binding name="community">
        <literal>Fe</literal>
      </binding>
    </result>

我现在该如何匹配模板?

2 个答案:

答案 0 :(得分:1)

您的样式表只有一个模板规则:match="sparql/results"应该匹配。您的输入文档是否包含示例中未显示的名称空间?

如果您的xml元素位于命名空间中,即使它是文档的默认命名空间,您也必须在任何XPath表达式和模板匹配规则中使用命名空间前缀。它是名称空间uri而不是重要的前缀。请注意,属性不在默认命名空间中,如果它们的名称具有前缀,它们只有一个命名空间。

<xsl:stylesheet version="1.0"
                xmlns:s="http://www.w3.org/2005/sparql-results#"
                xmlns:xsl="http://www.w3.org/1999/XSL/Transform">

    <xsl:template match="s:results">

built-in template rules生成您看到的输出,因为它们:

  • 匹配所有模板,并执行apply-templates
  • 将文本节点复制到输出

我添加了一条匹配/的规则,然后在每一步明确选择所需的元素。

此示例从您的输入生成一个HTML表,其中包含名字和姓氏的列。

<xsl:stylesheet version="1.0"
    xmlns:s="http://www.w3.org/2005/sparql-results#"
    xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
    <xsl:output method="html" encoding="UTF-8"/>

    <xsl:template match="/">
        <html>
            <head><title>persons</title>
            </head>
            <body>
                <xsl:apply-templates select="s:sparql/s:results" />
            </body>
        </html>
    </xsl:template>


    <xsl:template match="s:results">
        <table>
            <thead>
                <tr>
                    <td>
                        <xsl:text>Link</xsl:text>
                    </td>
                    <td>
                        <xsl:text>First name</xsl:text>
                    </td>
                    <td>
                        <xsl:text>Last name</xsl:text>
                    </td>
                </tr>
            </thead>
            <tbody>
                <xsl:apply-templates />
            </tbody>
        </table>
    </xsl:template>

    <xsl:template match="s:result">
        <tr>
            <td>
                <a href="{s:binding[@name='s']/s:uri}">
                    <xsl:value-of select="s:binding[@name='s']/s:uri" />
                </a>
            </td>
            <td>
                <xsl:value-of select="s:binding[@name='fname']/s:literal" />
            </td>
            <td>
                <xsl:value-of select="s:binding[@name='lname']/s:literal" />
            </td>
        </tr>
    </xsl:template>

</xsl:stylesheet>

答案 1 :(得分:1)

我没有尝试拉克兰的回答,但对我来说看起来不错。我把它快速放在一起,提供你要求的输出(它没有太大的不同,我没有做任何格式化)。

<xsl:output method="html"/>

<xsl:template match="/">
    <html>
        <head></head>
        <body>
            <xsl:apply-templates></xsl:apply-templates>
        </body>
    </html>
</xsl:template>

<xsl:template match="results">
    <table>
        <tr>
            <th>Fname</th>
            <th>Lname</th>
        </tr>
        <xsl:for-each select="result">
            <tr>
                <td><xsl:value-of select="binding[@name='fname']"/></td>
                <td><xsl:value-of select="binding[@name='lname']"/></td>
            </tr>
        </xsl:for-each>    
    </table>
</xsl:template>