Xml 使用XSL将子节点替换为顺序节点?
我们收到的文件错误地生成如下:Xml 使用XSL将子节点替换为顺序节点?,xml,xslt,Xml,Xslt,我们收到的文件错误地生成如下: <html> <body> <p>Lorem Ipsum is simply dummy text of the printing and typesetting industry. <p>Lorem Ipsum has been the industry's standard dummy text ever since the 1500s, when an unkn
<html>
<body>
<p>Lorem Ipsum is simply dummy text of the printing and typesetting industry.
<p>Lorem Ipsum has been the industry's standard dummy text ever since the 1500s, when an unknown printer took a galley of type and scrambled it to make a type specimen book.
<p>It has survived not only five centuries, but also the leap into electronic typesetting, remaining essentially unchanged.</p>
</p>
</p>
</body>
</html>
Lorem Ipsum只是印刷和排版行业的虚拟文本。
自16世纪以来,Lorem Ipsum一直是行业标准的虚拟文本,当时一位不知名的印刷商拿起一个打印工具,将其拼凑成一本打印样本书。
它不仅存活了五个世纪,而且还跨越到电子排版,基本上保持不变
元素正在嵌入到前面的
节点中。它应该是这样的:
<html>
<body>
<p>Lorem Ipsum is simply dummy text of the printing and typesetting industry.</p>
<p>Lorem Ipsum has been the industry's standard dummy text ever since the 1500s, when an unknown printer took a galley of type and scrambled it to make a type specimen book.</p>
<p>It has survived not only five centuries, but also the leap into electronic typesetting, remaining essentially unchanged.</p>
</body>
</html>
Lorem Ipsum只是印刷和排版行业的虚拟文本
自16世纪以来,Lorem Ipsum一直是行业标准的虚拟文本,当时一位不知名的印刷商拿起一个打印工具,将其拼凑成一本打印样本书
它不仅存活了五个世纪,而且还跨越到电子排版,基本上保持不变
我们无法控制发送文档的应用程序。我们如何使用XSL转换此文档,以便只将子节点(及其内容)呈现为同级节点?您可以尝试以下操作:
<?xml version='1.0'?>
<xsl:stylesheet
version='1.0'
xmlns:xsl='http://www.w3.org/1999/XSL/Transform'>
<xsl:output method="xml"
indent="yes" />
<xsl:template match="/">
<xsl:apply-templates select="html/body/*" mode="fixnested" />
</xsl:template>
<xsl:template match="*" mode="fixnested">
<xsl:element name="{name()}">
<xsl:apply-templates select="@* | text()" mode="fixnested" />
</xsl:element>
<xsl:apply-templates select="*" mode="fixnested" />
</xsl:template>
<xsl:template match="@*" mode="fixnested">
<xsl:attribute name="{name(.)}">
<xsl:value-of select="."/>
</xsl:attribute>
</xsl:template>
</xsl:stylesheet>
正如您所看到的,我把它保持得相当抽象,这样您就可以向它输入任何XML(而不仅仅是嵌套的
),并将其展平。属性和内容由这些模板保留。如果以这种方式生成的唯一元素是p,则需要为p编写一个模板,该模板首先为所有属性和非p子元素调用apply templates,然后将模板应用于嵌入的p元素。在XSLT 2.0语法中:
<xsl:template match="p">
<p><xsl:apply-templates select="node() except p"/></p>
<xsl:apply-templates select="p"/>
</xsl:template>
或者(正如伊恩·罗伯茨在评论中所建议的那样)用node()[not(self::p)]
替换node(),p除外
这假设除p之外的一些元素可能出现在输入的主体元素中;如果只发生p,Nils-Werner提供的解决方案就可以了
然而,在现实生活中,如果我必须这样处理输入,我可能会运行Tidy,而不是滚动我自己的XSLT样式表来完成Tidy的一小部分工作。mode=“fixnested”做什么?顺便说一句,对于给定的输入,这不能正常工作。所有标记(除了p)都从文档中剥离出来,并包含一个XML原型。但是输入太坏了 我们得把它修好
变成输入中断 所以我们必须修复它 got
@ilitirit它可以防止相当一般的
被意外地应用到XML的其他部分。@C.M.Sperberg-McQueen yep。未指定那些
中正确放置的
,因此未考虑它们。@i提示在第一个模板中跳过内容。只需在那里重新添加它。其他文本格式元素(b,i)确实出现在p标记中,因此我不能使用Nils的解决方案。对于XSLT 1.0,如何select=“node()[not(self::p)]”
<xsl:template match="p">
<p><xsl:apply-templates mode="para-contents"/></p>
<xsl:apply-templates select="p"/>
</xsl:template>
<xsl:template match="node()" mode="para-contents">
<xsl:apply-templates select="."/>
</xsl:template>
<xsl:template match="p" mode="para-contents"/>