我有很多具有以下形式的 XML 文件:
<Element fruit="apple" animal="cat" />
我想从文件中删除。
使用 XSLT 样式表和 Linux 命令行实用程序 xsltproc,我该怎么做?
到目前为止,在脚本中我已经有了包含我要删除的元素的文件列表,因此可以将单个文件用作参数。
编辑:这个问题最初缺乏意图。
我想要实现的是删除整个元素“元素” where (fruit=="apple" && animal=="cat")。在同一个文档中有许多名为“元素”的元素,我希望这些元素能够保留。所以
<Element fruit="orange" animal="dog" />
<Element fruit="apple" animal="cat" />
<Element fruit="pear" animal="wild three eyed mongoose of kentucky" />
会成为:
<Element fruit="orange" animal="dog" />
<Element fruit="pear" animal="wild three eyed mongoose of kentucky" />
使用最基本的 XSLT 设计模式之一:“覆盖 identity transformation”将只写以下内容:
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"> <xsl:output omit-xml-declaration="yes"/> <xsl:template match="node()|@*"> <xsl:copy> <xsl:apply-templates select="node()|@*"/> </xsl:copy> </xsl:template> <xsl:template match="Element[@fruit='apple' and @animal='cat']"/> </xsl:stylesheet>
请注意,第二个模板如何仅针对名为“Element”的元素覆盖标识(第一个)模板,这些元素具有属性“fruit”的值为“apple”,属性“animal”的值为“cat”。这个模板的主体是空的,这意味着匹配的元素被简单地忽略(匹配时什么都不产生)。
当此转换应用于以下源 XML 文档时:
<doc>... <Element name="same">foo</Element>... <Element fruit="apple" animal="cat" /> <Element fruit="pear" animal="cat" /> <Element name="same">baz</Element>... <Element name="same">foobar</Element>... </doc>
产生了想要的结果:
<doc>... <Element name="same">foo</Element>... <Element fruit="pear" animal="cat"/> <Element name="same">baz</Element>... <Element name="same">foobar</Element>... </doc>
here 可以找到更多使用和覆盖身份模板的代码片段。
@Dimitre Novatchev 的答案当然既正确又优雅,但有一个概括(OP 没有询问):如果您要过滤的元素也有您想要保留的子元素或文本怎么办?
我相信这个微小的变化涵盖了这种情况:
<?xml version="1.0" encoding="UTF-8"?>
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
xmlns:xs="http://www.w3.org/2001/XMLSchema"
version="2.0">
<xsl:template match="node()|@*">
<xsl:copy>
<xsl:apply-templates select="node()|@*"/>
</xsl:copy>
</xsl:template>
<!-- drop DropMe elements, keeping child text and elements -->
<xsl:template match="DropMe">
<xsl:apply-templates/>
</xsl:template>
</xsl:stylesheet>
指定其他属性等的匹配条件可能很复杂,如果您要删除其他内容,则可以使用多个此类模板。
所以这个输入:
<?xml version="1.0" encoding="UTF-8"?>
<mydocument>
<p>Here's text to keep</p>
<p><DropMe>Keep this text but not the element</DropMe>; and keep what follows.</p>
<p><DropMe>Also keep this text and <b>this child element</b> too</DropMe>, along with what follows.</p>
</mydocument>
产生这个输出:
<?xml version="1.0" encoding="UTF-8"?><mydocument>
<p>Here's text to keep</p>
<p>Keep this text but not the element; and keep what follows.</p>
<p>Also keep this text and <b>this child element</b> too, along with what follows.</p>
</mydocument>
归功于 XSLT Cookbook。
不定期副业成功案例分享
/bookstore/book[position() = 1 or position() = 3]/@*
的缩写版本是什么吗?/*/book[position() = 1 or position() = 3]/@*
。在 XPath 2.0 中:/*/book[position() = (1,3)]/@*