コピーしたい XML ドキュメントを持っていますが、1 つの特別な属性を変換する方法がわかりません。XML をコピーして一般的な属性を置き換えることは問題なく機能しますが、XSL でフレーズのリストを定義し、それを別のフレーズに変換する方法がわかりません。
定義は読みやすくする必要があります。translate()
ある種のリスト表現を飲み込みますか? を使用した小さな例translate
は素晴らしいでしょう (XML のコピーは気にしないでください)。
XPath と XSLT 1.0のtranslate
機能は、ある Unicode 文字を別の Unicode 文字に置き換えるだけです。入力文字と置換文字のリストを指定すると、最初のリストの各文字が 2 番目のリストの同じ位置にある文字に置き換えられます。しかし、完全な作品やフレーズを置き換えるには、他のツールが必要です。
たとえば、(XSLT 2.0 を使用して) 単純に実行できると仮定して、完全な属性値を置き換えたいかどうかを述べたり説明したりしていません。
<xsl:stylesheet
xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
version="2.0">
<xsl:key name="phrase" match="phrase" use="@input"/>
<xsl:param name="phrases">
<phrases>
<phrase input="IANAL" output="I am not a lawyer"/>
<phrase input="WYSIWYG" output="What you see is what you get"/>
</phrases>
</xsl:param>
<xsl:template match="@* | node()">
<xsl:copy>
<xsl:apply-templates select="@* , node()"/>
</xsl:copy>
</xsl:template>
<xsl:template match="foo/@bar">
<xsl:attribute name="baz" select="key('phrase', ., $phrases)/@output"/>
</xsl:template>
</xsl:stylesheet>
たとえば、そのスタイルシートが変換されます
<root>
<foo bar="IANAL"/>
<foo bar="WYSIWYG"/>
</root>
の中へ
<root>
<foo baz="I am not a lawyer"/>
<foo baz="What you see is what you get"/>
</root>
1 つの値または文字列の部分文字列を複数置換したい場合は、さらに手間がreplace
かかりますが、XSLT/XPath 2.0 の機能を使用すればそれも可能です。
[編集] アイテムのリストとフレーズを置き換える再帰関数を使用した例を次に示します。
<xsl:stylesheet
xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
xmlns:xs="http://www.w3.org/2001/XMLSchema"
xmlns:mf="http://example.com/mf"
exclude-result-prefixes="xs mf"
version="2.0">
<xsl:key name="phrase" match="phrase" use="@input"/>
<xsl:function name="mf:replace-phrases" as="xs:string">
<xsl:param name="phrases" as="element(phrase)*"/>
<xsl:param name="text" as="xs:string"/>
<xsl:choose>
<xsl:when test="not($phrases)">
<xsl:sequence select="$text"/>
</xsl:when>
<xsl:otherwise>
<xsl:sequence select="mf:replace-phrases($phrases[position() gt 1], replace($text, $phrases[1]/@input, $phrases[1]/@output))"/>
</xsl:otherwise>
</xsl:choose>
</xsl:function>
<xsl:param name="phrases">
<phrases>
<phrase input="IANAL" output="I am not a lawyer"/>
<phrase input="WYSIWYG" output="What you see is what you get"/>
</phrases>
</xsl:param>
<xsl:template match="@* | node()">
<xsl:copy>
<xsl:apply-templates select="@* , node()"/>
</xsl:copy>
</xsl:template>
<xsl:template match="foo/@bar">
<xsl:attribute name="baz" select="mf:replace-phrases($phrases/phrases/phrase, .)"/>
</xsl:template>
</xsl:stylesheet>
それは例を変換します
<root>
<foo bar="He said: 'IANAL'. I responded: 'WYSIWYG', and he smiled."/>
</root>
の中へ
<root>
<foo baz="He said: 'I am not a lawyer'. I responded: 'What you see is what you get', and he smiled."/>
</root>