保留属性空格

时间:2008-11-04 00:22:01

标签: xml xslt whitespace

免责声明:以下是针对XML的罪行。这就是为什么我试图用XSLT改变它:)

我的XML目前看起来像这样:

<root>
    <object name="blarg" property1="shablarg" property2="werg".../>
    <object name="yetanotherobject" .../>
</root>

是的,我将所有文本数据放在属性中。我希望XSLT能救我;我想走向这样的事情:

<root>
    <object>
        <name>blarg</name>
        <property1>shablarg</name>
        ...
    </object>
    <object>
        ...
    </object>
</root>

到目前为止,我实际上已经完成了所有这些工作,除了我对XML的罪恶更加特殊。有些标签看起来像这样:

<object description = "This is the first line

This is the third line.  That second line full of whitespace is meaningful"/>

我在linux下使用xsltproc,但它似乎没有任何保留空格的选项。我试图使用xsl:preserve-space和xml:space =“preserve”无济于事。我发现的每个选项似乎都适用于在元素本身内保留空格,而不是属性。每一次,以上都改为:

This is the first line This is the third line.  That second line full of whitespace is meaningful

所以问题是,我可以保留属性空白吗?

4 个答案:

答案 0 :(得分:5)

这实际上是一个原始的XML解析问题,而不是XSLT可以帮助您解决的问题。根据XML标准中的“3.3.3属性值规范化”,XML解析必须将该属性值中的换行符转换为空格。因此,当前正在阅读您的描述属性并保持换行的任何内容都是错误的。

您可以通过预处理XML来恢复换行符,以便将换行符转移到&amp; #10;字符引用,只要你还没有得到不允许使用charrefs的换行符,例如标记体内部。 Charrefs应该作为控制字符存活到属性值,然后您可以将它们转换为文本节点。

答案 1 :(得分:3)

根据Annotated XML Spec,属性值中的空格由XML处理器规范化(参见3.3.3上的(T)注释)。所以,看起来答案可能不是。

答案 2 :(得分:1)

正如其他人所指出的那样,XML规范不允许保留属性中的空格。事实上,这是你可以用属性和元素做的少数区别之一(另一个主要是元素可以包含其他标签而属性不能)。

您必须首先处理XML之外的文件,以便保留空格。

答案 3 :(得分:0)

如果您可以控制XML处理器,则可以执行此操作。

来自我的other answer(链接了很多引用):

如果你有像

那样的XML
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<!DOCTYPE elemke [
<!ATTLIST brush wood CDATA #REQUIRED>
]>

<elemke>
<brush wood="guy&#xA;threep"/>
</elemke>

和XSL一样

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

<xsl:template name="split">
  <xsl:param name="list"      select="''" />
  <xsl:param name="separator" select="'&#xA;'" />
  <xsl:if test="not($list = '' or $separator = '')">
    <xsl:variable name="head" select="substring-before(concat($list, $separator), $separator)" />
    <xsl:variable name="tail" select="substring-after($list, $separator)" />

    <xsl:value-of select="$head"/>
    <br/><xsl:text>&#xA;</xsl:text>
    <xsl:call-template name="split">
        <xsl:with-param name="list"      select="$tail" />
        <xsl:with-param name="separator" select="$separator" />
    </xsl:call-template>
  </xsl:if>
</xsl:template>


<xsl:template match="brush">
  <html>
  <xsl:call-template name="split">
    <xsl:with-param name="list" select="@wood"/>
  </xsl:call-template>
  </html>
</xsl:template>

</xsl:stylesheet>

你可以得到一个类似的HTML:

<html>guy<br>
   threep<br>

</html>  

使用像saxon命令行这样的处理器进行测试/生成:

java -jar saxon9he.jar -s:in.xml -xsl:in.xsl -o:out.html