Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/visual-studio-2008/2.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 使用xsl输出纯文本_Xml_Xslt_Foreach_Plaintext_Line Breaks - Fatal编程技术网

Xml 使用xsl输出纯文本

Xml 使用xsl输出纯文本,xml,xslt,foreach,plaintext,line-breaks,Xml,Xslt,Foreach,Plaintext,Line Breaks,我需要使用XSL从XML生成简单的纯文本输出。因为我没有在网上找到任何好的简明的例子,所以我决定在这里发布我的解决方案。当然,如果链接中提到更好的示例,我们将不胜感激: <?xml version="1.0" encoding="UTF-8"?> <xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform" xmlns:fo="http://www.w3.org/1999/XSL/F

我需要使用XSL从XML生成简单的纯文本输出。因为我没有在网上找到任何好的简明的例子,所以我决定在这里发布我的解决方案。当然,如果链接中提到更好的示例,我们将不胜感激:

<?xml version="1.0" encoding="UTF-8"?>
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform" xmlns:fo="http://www.w3.org/1999/XSL/Format" >
    <xsl:output method="text" omit-xml-declaration="yes" indent="no"/>
    <xsl:template match="/">
        <xsl:for-each select="script/command" xml:space="preserve">at -f <xsl:value-of select="username"/> <xsl:value-of select="startTime/@hours"/>:<xsl:value-of select="startTime/@minutes"/> <xsl:value-of select="startDate"/><xsl:text>
</xsl:text></xsl:for-each> 
    </xsl:template>
</xsl:stylesheet>

at-f:
有几件重要的事情帮助了我:

  • 使用xsl:output省略输出文档开头的标准声明
  • 使用xml:space=“preserve”属性为每个标记保留我在xsl:for中编写的任何空白。这还要求我在for-each标记中编写所有代码,也包括该标记,在一行上(换行除外)
  • 使用插入换行符-这里我不得不再次省略标准xml缩进
  • 此xslt的结果和所需输出为:

    at-f alluser 23:58 17.4.2010
    at-f ggroup67 7:58 28.4.2010
    at-f ggroup70 15:58 18.4.2010
    at-f alluser 23:58 18.4.2010
    at-f ggroup61 7:58 22.9.2010
    at-f ggroup60 23:58 21.9.2010
    at-f alluser 3:58 22.9.2010

    正如我所说,任何关于如何更优雅地完成这项工作的建议都将不胜感激


    后续行动2011-05-08:

    以下是我正在处理的xml类型:

    <script xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="script.xsd">
        <command>
            <username>alluser</username>
            <startTime minutes="58" hours="23"/>
            <startDate>17.4.2010</startDate>
        </command>
    </script>
    
    
    诱惑者
    17.4.2010
    
    • 您可以定义一个模板来匹配
      script/command
      ,并消除
      xsl:for each
    • concat()
      可以用来缩短表达式,避免显式插入太多的
      元素
    • 实体引用的使用
      和#xA
      元素之间的换行符更安全,因为代码格式不会弄乱换行符。另外,对我来说,它读起来是一个明确的换行符,更容易理解其意图


    只是为了好玩:这可以用一种非常通用和紧凑的方式来完成

    <xsl:stylesheet version="1.0"
      xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
        <xsl:output omit-xml-declaration="yes" indent="yes"/>
        <xsl:output method="text"/>
        <xsl:strip-space elements="*"/>
    
        <xsl:template match="*">
            <xsl:apply-templates select="node()|@*"/>
            <xsl:text> </xsl:text>
        </xsl:template>
    
        <xsl:template match="username">
           at -f <xsl:apply-templates select="*|@*"/>
        </xsl:template>
    </xsl:stylesheet>
    
    <script>
     <command>
      <username>John</username>
      <startTime hours="09:" minutes="33"/>
      <startDate>05/05/2011</startDate>
    
      <username>Kate</username>
      <startTime hours="09:" minutes="33"/>
      <startDate>05/05/2011</startDate>
    
      <username>Peter</username>
      <startTime hours="09:" minutes="33"/>
      <startDate>05/05/2011</startDate>
     </command>
    </script>
    

    注意:如果要输出的所有数据都包含在文本节点中,而不是属性中,则此一般方法最适用。

    您可以使用
    concat('at-f',username',startTime/@hours',,…)来节省
    元素的数量。
    。此外,你可以将你的源代码包装起来——如果你在标签中这样做,它不会影响输出。好问题,+1。有关完整、非常简短且真正通用的解决方案,请参见我的答案。@Christopher Creutzig:感谢您对concat()的宝贵建议。“包装你的源代码”指的是什么?参见Mads的回答:没有必要把所有内容都放在一行上。(虽然我不会打断逗号前的一行。它看起来很奇怪,没有添加任何内容,甚至不能更轻松地注释出来。)我们不会对堆栈溢出进行代码检查。我建议您重新构造您的问题,使其成为实际问题(例如,如何从XML文档中删除文本),然后将您的草稿作为答案发布。缺少@*值(应该用“:”分隔)。另外,不确定输出中“at-f”之前的前导空格是否会有问题。@Mads Hansen:谢谢你注意到这一点。现在已修复。几乎修复,但我认为源XML的值
    @hours
    中没有“:”。发布的示例XSL显式地将“:”放入,而不是从属性值中进行选择。@Mads Hansen:当然。虽然我说“为了好玩”,但我的回答指出了一种设计XML的通用方法,这样就可以使用相同的一般和琐碎的XSLT转换来生成输出,而不需要知道任何其他细节。正如我在回答中所说,我不会使用属性,只会将数据存储在文本节点中。用户提示(PHP、Python、浏览器等):如果不使用
    ,则不会删除空格(!)。感谢Mads,非常好的建议。这正是我想要的。我忘记了XPath2的有用特性。。。这是怎么回事 ;当windows通常不仅需要换行符,而且还需要回车符时,给了我一个关于windows的新行?@Chris Dickinson注意,这是一个XSLT/XPath 1.0解决方案,没有使用XPath 2.0功能<代码> (换行)通常就足够了。您可以添加
    
(回车)如果您需要CRLF。
    
    <script>
     <command>
      <username>John</username>
      <startTime hours="09:" minutes="33"/>
      <startDate>05/05/2011</startDate>
    
      <username>Kate</username>
      <startTime hours="09:" minutes="33"/>
      <startDate>05/05/2011</startDate>
    
      <username>Peter</username>
      <startTime hours="09:" minutes="33"/>
      <startDate>05/05/2011</startDate>
     </command>
    </script>
    
       at -f 09:33 05/05/2011 
       at -f 09:33 05/05/2011 
       at -f 09:33 05/05/2011