Warning: file_get_contents(/data/phpspider/zhask/data//catemap/8/xslt/3.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Xml 在同名元素的文本之间插入空格_Xml_Xslt_Transformation - Fatal编程技术网

Xml 在同名元素的文本之间插入空格

Xml 在同名元素的文本之间插入空格,xml,xslt,transformation,Xml,Xslt,Transformation,对于精通XSLT的作者来说,回答这个问题可能相当简单 我有以下示例XML文档: <?xml version="1.0" encoding="UTF-8"?> <students> <student num="12345678"> <name>Dona Diller</name> <dob>1970-07-21</dob> <education>B

对于精通XSLT的作者来说,回答这个问题可能相当简单

我有以下示例XML文档:

<?xml version="1.0" encoding="UTF-8"?>
<students>
    <student num="12345678">
        <name>Dona Diller</name>
        <dob>1970-07-21</dob>
        <education>BSc</education>
        <education>MSc</education>
        <status>Married</status>
    </student>

<!-- more student elements to follow... -->

</students>

多娜·迪勒
1970-07-21
理学士
理学硕士
已婚的
以及以下XSL:

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

    <xsl:template match="/">
        <html>
            <title>Test</title>
            <body>
                <h1>Personal details</h1>
                <xsl:apply-templates select="students/student"/>
            </body>
        </html>
    </xsl:template>

    <xsl:template match="student">
        <p>
            Student number:
            <xsl:value-of select="@num"/>
        </p>
        <p>Full name:
            <xsl:value-of select="name"/>
        </p>
        <p>Date of birth
            <xsl:value-of select="dob"/>
        </p>
        <!-- TODO: text of 'education' elements must be separated by a space -->
        <p>Degrees:
            <xsl:apply-templates select="education"/>
        </p>
        <p>Status:
            <xsl:value-of select="status"/>
        </p>
    </xsl:template>

</xsl:stylesheet>

试验
个人资料

学号:

全名:

出生日期

学位:

地位:

当应用于本文开头包含的XML文档时,将生成以下XHTML输出:

<html>
   <title>Test</title>
   <body>
      <h1>Personal details</h1>
      <p>
         Student number:
         12345678
      </p>
      <p>Full name:
         Dona Diller
      </p>
      <p>Date of birth
         1970-07-21
      </p>
      <p>Degrees:
         BScMSc
      </p>
      <p>Status:
         Married
      </p>
   </body>
</html>

试验
个人资料

学号:
12345678

全名: 多娜·迪勒

出生日期 1970-07-21

学位: 理学学士

地位: 已婚的

我的问题是学位名称合并为一个字符串(教育元素的文本)。因此,在前面的示例中,我希望显示“BSc MSc”,而不是在输出中显示“BSCSC”。有什么想法吗?

添加一个模板

<xsl:template match="education">
  <xsl:if test="position() > 1">
    <xsl:text> </xsl:text>
  </xsl:if>
  <xsl:value-of select="."/>
</xsl:template>

添加模板

<xsl:template match="education">
  <xsl:if test="position() > 1">
    <xsl:text> </xsl:text>
  </xsl:if>
  <xsl:value-of select="."/>
</xsl:template>

更短/更简单/可读性更强

添加此模板

<xsl:template match="education[position() > 1]">
  <xsl:value-of select="concat(' ', .)"/>
</xsl:template>

更短/更简单/可读性更强

添加此模板

<xsl:template match="education[position() > 1]">
  <xsl:value-of select="concat(' ', .)"/>
</xsl:template>

诺瓦切夫和霍宁的解决方案(当然)都能奏效,但他们的某些地方让我觉得有点不满意。我认为,如果要将教育元素的格式委托给模板规则,那么模板规则应该只关注一个教育元素的格式,而不关注一组相邻元素的格式。对我来说,间隙间距正是父模板的工作。所以我想我会倾向于写:

<xsl:for-each select="education">
  <xsl:if test="position() ne 1"><xsl:text> </xsl:text></xsl:if>
  <xsl:apply-templates select="."/>
</xsl:for-each>


但这是一个意见问题。

诺瓦切夫和霍宁的解决方案(当然)都会奏效,但他们的某些方面让我感到有点不满意。我认为,如果要将教育元素的格式委托给模板规则,那么模板规则应该只关注一个教育元素的格式,而不关注一组相邻元素的格式。对我来说,间隙间距正是父模板的工作。所以我想我会倾向于写:

<xsl:for-each select="education">
  <xsl:if test="position() ne 1"><xsl:text> </xsl:text></xsl:if>
  <xsl:apply-templates select="."/>
</xsl:for-each>


但这是一个意见问题。

只需在每个度的末尾添加一个空格:

<xsl:template match="education">
    <xsl:value-of select="concat(.,' ')"/>
</xsl:template>

是的,这会在度数列表的末尾产生一个无关的空格,但在本例中这不是问题

如果您有XSLT2.0,您可以试试

<p>Degrees:
    <xsl:value-of select="string-join(education,' ')"/>
</p>
度:


只需在每个度的末尾添加一个空格:

<xsl:template match="education">
    <xsl:value-of select="concat(.,' ')"/>
</xsl:template>

是的,这会在度数列表的末尾产生一个无关的空格,但在本例中这不是问题

如果您有XSLT2.0,您可以试试

<p>Degrees:
    <xsl:value-of select="string-join(education,' ')"/>
</p>
度:


或!=如果您停留在XSLT1.0(如OP的样式表中所示)而不是ne:-)在我的回答中,我尝试提供我能想到的最短可能的解决方案。这有意排除任何条件或使用
xsl:text
。在我的回答中,我尝试提供我能想到的最短可能的解决方案。这有意排除任何条件或使用
xsl:text
。Martin的解占据了6行,并且有一个不必要的显式条件。您的解决方案占用了4行,其中一行相当长,使用
xsl:for each
,有一个显式的条件,而且不太可读。此外,有时还有一个模板匹配作者指定的
text()
,其行为与内置XSLT模板不同。我的代码不对任何匹配
text()
或!=如果您停留在XSLT1.0(如OP的样式表中所示)而不是ne:-)在我的回答中,我尝试提供我能想到的最短可能的解决方案。这有意排除任何条件或使用
xsl:text
。在我的回答中,我尝试提供我能想到的最短可能的解决方案。这有意排除任何条件或使用
xsl:text
。Martin的解占据了6行,并且有一个不必要的显式条件。您的解决方案占用了4行,其中一行相当长,使用
xsl:for each
,有一个显式的条件,而且不太可读。此外,有时还有一个模板匹配作者指定的
text()
,其行为与内置XSLT模板不同。我的代码不对任何匹配
text()
的模板的行为进行假设。