什么XSL脚本会缩进我的数据?
例如:
<dtd name="cited">
<XMLDOC>
<cited year="2010">
<case>
No. 275 v. M.N.R.
<cite>
<yr>
2010
<pno cite="20101188">10</pno>
</yr>
</cite>
</case>
</cited>
</XMLDOC>
<XMLDOC>
<case>
Wellesley St.
<cite>
<yr>
2010
<pno cite="20105133">9</pno>
</yr>
</cite>
</case>
</XMLDOC>
</dtd>
要:
<dtd name="cited">
<XMLDOC>
<cited year="2010"></cited>
<case>
No. 275 v. M.N.R.
</case>
<cite>
</cite>
<yr>
2010
</yr>
<pno cite="20101188">10</pno>
</XMLDOC>
<XMLDOC>
<case>
Wellesley St
</case>
<cite>
</cite>
<yr>
2010
</yr>
<pno cite="20105133">9</pno>
</XMLDOC>
</dtd>
谢谢!
来自评论:
我想要的是应用正确的 关闭标签,如
<yr></yr> <pno cite="20101188">10</pno>
而不是
<yr> 2010 <pno cite="20101188">10</pno> </yr>
答案 0 :(得分:16)
使用indent="yes
声明中指定的<xsl:output>
进行简单的身份转换:
<xsl:stylesheet version="1.0"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:output omit-xml-declaration="yes" indent="yes"/>
<xsl:template match="node()|@*">
<xsl:copy>
<xsl:apply-templates select="node()|@*"/>
</xsl:copy>
</xsl:template>
</xsl:stylesheet>
此转换应用于提供的XML文档(未定义的实体
替换为其对应的字符实体 
):
<dtd name="cited">
<XMLDOC>
<cited year="2010">
<case>
No. 275 v. M.N.R.
<cite>
<yr>
2010
<pno cite="20101188">10</pno>
</yr>
</cite>
</case>
</cited>
</XMLDOC>
<XMLDOC>
<case>
Wellesley St.
<cite>
<yr>
2010
<pno cite="20105133">9</pno>
</yr>
</cite>
</case>
</XMLDOC>
</dtd>
在使用AltovaXML 运行时生成:
<dtd name="cited">
<XMLDOC>
<cited year="2010">
<case>
No. 275 v. M.N.R.
<cite>
<yr>
2010
<pno cite="20101188">10</pno></yr>
</cite></case>
</cited>
</XMLDOC>
<XMLDOC>
<case>
Wellesley St.
<cite>
<yr>
2010
<pno cite="20105133">9</pno></yr>
</cite></case>
</XMLDOC>
</dtd>
使用Saxon 6.5.4运行时,相同的转换产生:
<dtd name="cited">
<XMLDOC>
<cited year="2010">
<case>
No. 275 v. M.N.R.
<cite>
<yr>
2010
<pno cite="20101188">10</pno>
</yr>
</cite>
</case>
</cited>
</XMLDOC>
<XMLDOC>
<case>
Wellesley St.
<cite>
<yr>
2010
<pno cite="20105133">9</pno>
</yr>
</cite>
</case>
</XMLDOC>
</dtd>
因此,输出大不相同,具体取决于使用哪个XSLT 1.0处理器。 Saxon解析并且不会丢弃每个仅限空白的节点,这加上缩进会产生太多的空白区域。
解决方法是使用以下方法显式导致仅删除空白节点:
<xsl:strip-space elements="*"/>
所以,当这个转变时:
<xsl:stylesheet version="1.0"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:output omit-xml-declaration="yes" indent="yes"/>
<xsl:strip-space elements="*"/>
<xsl:template match="node()|@*">
<xsl:copy>
<xsl:apply-templates select="node()|@*"/>
</xsl:copy>
</xsl:template>
</xsl:stylesheet>
与Saxon针对相同的源XML文档运行,输出现在:
<dtd name="cited">
<XMLDOC>
<cited year="2010">
<case>
No. 275 v. M.N.R.
<cite>
<yr>
2010
<pno cite="20101188">10</pno>
</yr>
</cite>
</case>
</cited>
</XMLDOC>
<XMLDOC>
<case>
Wellesley St.
<cite>
<yr>
2010
<pno cite="20105133">9</pno>
</yr>
</cite>
</case>
</XMLDOC>
</dtd>
AltovaXML和许多其他XSLT 1.0处理器(.NET的XslCompiledTransform,XslTransform)也会生成运行最后一次转换的漂亮的缩进输出。
<强>更新:
就在最近他的评论中,OP泄露了重要的新要求,这使得这个问题完全不仅仅是“缩进”......
来自评论:
我想要的是应用正确的 关闭标签,如
<yr></yr> <pno cite="20101188">10</pno>
而不是
<yr> 2010 <pno cite="20101188">10</pno> </yr>
这是转换,产生想要的输出:
<xsl:stylesheet version="1.0"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:output omit-xml-declaration="yes" indent="yes"/>
<xsl:strip-space elements="*"/>
<xsl:template match="node()|@*">
<xsl:copy>
<xsl:apply-templates select="node()|@*"/>
</xsl:copy>
</xsl:template>
<xsl:template match="yr">
<yr>
<xsl:apply-templates select="text()[1]"/>
</yr>
<xsl:apply-templates select="*"/>
</xsl:template>
</xsl:stylesheet>
答案 1 :(得分:1)
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" version="1.0">
<!-- output xml and indent -->
<xsl:output method="xml" indent="yes"/>
<!-- copy all elements and their attributes -->
<xsl:template match="* | @*">
<xsl:copy><xsl:copy-of select="@*"/><xsl:apply-templates/></xsl:copy>
</xsl:template>
</xsl:stylesheet>
答案 2 :(得分:0)
在Java世界中,Apache Xalan可以提供帮助。您只需在indent
标记中添加xslt:indent-amount
,xmlns:xslt
,xsl:output
个参数即可。
<?xml version="1.0" encoding="ISO-8859-1"?>
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" version="1.0">
<xsl:output method="xml" encoding="utf-8" indent="yes"
xslt:indent-amount="3" xmlns:xslt="http://xml.apache.org/xslt" />
...
你可以用Ant运行XSL:
<?xml version="1.0"?>
<project name="My XSL conversion" default="myxsltarget" basedir=".">
<target name="myxsltarget">
<xslt basedir="in" destdir="out" extension=".xml" style="myxsl.xsl"/>
</target>
</project>