这可能是一个奇怪的问题,但我很好奇是否有解决方案。我有一个深度嵌套和复杂的XML文件,例如OOXML和我尝试用一些正则表达式来分析它的文本。
分析文档的文本我想(1)将所有文本节点存储在变量中,(2)运行一些正则表达式,(3)将所有文本节点写回其原始元素。显然最后一部分是问题,我不知道它是否可能。
(简化)XML:
<?xml version="1.0" encoding="UTF-8"?>
<body>
<p>
<t>foo </t>
<t>some text </t>
<t>
<i>number</i>
<b>
<nr>5</nr>
</b>
</t>
<t>more </t>
<t>text</t>
</p>
</body>
XSLT
<?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" exclude-result-prefixes="xs" version="2.0">
<xsl:template match="p">
<xsl:variable name="plain" select="normalize-space(string-join(t//text(), ''))"/>
<xsl:analyze-string select="$plain" regex="foo( .* )number (\d)">
<xsl:matching-substring>
<xsl:value-of select="'bar', regex-group(1), 'nr.', regex-group(2)"/>
</xsl:matching-substring>
<xsl:non-matching-substring>
<xsl:value-of select="."/>
</xsl:non-matching-substring>
</xsl:analyze-string>
</xsl:template>
</xsl:stylesheet>
通缉输出类似于:
<?xml version="1.0" encoding="UTF-8"?>
<body>
<p>
<t>bar </t>
<t>some text </t>
<t>
<i>nr. </i>
<b>
<nr>5</nr>
</b>
</t>
<t>more </t>
<t>text</t>
</p>
</body>
我知道在这种情况下,t
上的模板匹配以及检查preceding
和following
轴的一些XPath可以完成这项工作。但是当XML变得更加复杂时,它会非常烦人。
答案 0 :(得分:1)
怎么样
<?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" exclude-result-prefixes="xs" version="2.0">
<xsl:template match="node()|@*">
<xsl:copy>
<xsl:apply-templates select="node()|@*"/>
</xsl:copy>
</xsl:template>
<xsl:template match="t[parent::p[matches(normalize-space(string-join(t//text(), '')), 'foo( .* )number (\d)')]]/text()">
<xsl:value-of select="replace(replace(., 'foo', 'bar'), 'number', 'nr.')"/>
</xsl:template>
<xsl:template match="*[ancestor::t]/text()">
<xsl:value-of select="replace(replace(., 'foo', 'bar'), 'number', 'nr.')"/>
</xsl:template>
</xsl:stylesheet>
我不知道这是否仍适用于复杂的XML。