Warning: file_get_contents(/data/phpspider/zhask/data//catemap/8/xslt/3.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Xml 如何在字符串变量XSLT中进行替换?_Xml_Xslt_Replace - Fatal编程技术网

Xml 如何在字符串变量XSLT中进行替换?

Xml 如何在字符串变量XSLT中进行替换?,xml,xslt,replace,Xml,Xslt,Replace,我使用以下XSLT脚本从XML中提取URL: <?xml version="1.0" encoding="UTF-8"?> <xsl:stylesheet version="2.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform" xmlns:dcterms="http://purl.org/dc/terms/" xmlns:dc="http://purl.org/dc/elements/1.1/" xm

我使用以下XSLT脚本从XML中提取URL:

<?xml version="1.0" encoding="UTF-8"?>     
<xsl:stylesheet  version="2.0"
 xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
 xmlns:dcterms="http://purl.org/dc/terms/" 
 xmlns:dc="http://purl.org/dc/elements/1.1/"
  xmlns:ns="http://www.openarchives.org/OAI/2.0/"
xmlns:ns0="http://schema.fabrik.de/data/1.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"   
 exclude-result-prefixes="dc dcterms ">     
    <xsl:output method="xml" version="1.0"
    encoding="UTF-8" indent="yes" />        
    <xsl:template match="/">
 <xsl:if test="string(xml-fragment/ns:metadata/ns0:objects/ns0:objekttyp/ns0:datei/ns0:files/ns0:file/ns0:versions/ns0:version[@name='small']/ns0:deep_link_url)">
    <dc:identifier xsi:type="dcterms:URI"> 
     <xsl:value-of select="/xml-fragment/ns:metadata/ns0:objects/ns0:objekttyp/ns0:datei/ns0:files/ns0:file/ns0:versions/ns0:version[@name='small']/ns0:deep_link_url"/> 
      </dc:identifier>
 </xsl:template> 

</xsl:stylesheet>  
我试图做的是将URL保存在变量$file中,然后通过“附件”替换“inline”。 我遇到以下错误:[main]JAXPSAXProcessorInvoker-找不到函数:replace

<xsl:variable name='file' select="/xml-fragment/ns:metadata/ns0:objects/ns0:objekttyp/ns0:datei/ns0:files/ns0:file/ns0:versions/ns0:version[@name='small']/ns0:deep_link_url"/> 
<xsl:value-of select="replace($file, 'inline', 'attachment')"/>

就像评论中建议的那样,您可以使用递归模板来解决这个问题。在本例中,模板
replace
将在字符串“inline”前后的子字符串中拆分输入字符串
$file
。只要
$sub_after
还包含字符串“inline”,模板就会递归地调用自身。如果之后的
$sub_中没有此类字符串,则将提取其字符串并完成模板

<?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"
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"   
    version="1.0">

    <xsl:template match="/">
        <xsl:call-template name="replace">
            <xsl:with-param name="file" select="'https://id/1001976586/file_version/name/small/inline/disposition/inline/test'"/>
        </xsl:call-template>
    </xsl:template>

    <xsl:template name="replace">
        <xsl:param name="file"/>
        <xsl:variable name="sub_before" select="substring-before($file, 'inline')"/>
        <xsl:variable name="sub_after" select="substring-after($file, 'inline')"/>
        <xsl:value-of select="concat($sub_before, 'attachment')"/>
        <xsl:choose>
            <xsl:when test="contains($sub_after, 'inline')">
                <xsl:call-template name="replace">
                    <xsl:with-param name="file" select="$sub_after"/>
                </xsl:call-template>
            </xsl:when>
            <xsl:otherwise>
                <xsl:value-of select="$sub_after"/>
            </xsl:otherwise>
        </xsl:choose>
    </xsl:template> 
</xsl:stylesheet>

就像评论中建议的那样,您可以使用递归模板来解决这个问题。在本例中,模板
replace
将在字符串“inline”前后的子字符串中拆分输入字符串
$file
。只要
$sub_after
还包含字符串“inline”,模板就会递归地调用自身。如果
之后的
$sub_中没有此类字符串,则将提取其字符串并完成模板

<?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"
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"   
    version="1.0">

    <xsl:template match="/">
        <xsl:call-template name="replace">
            <xsl:with-param name="file" select="'https://id/1001976586/file_version/name/small/inline/disposition/inline/test'"/>
        </xsl:call-template>
    </xsl:template>

    <xsl:template name="replace">
        <xsl:param name="file"/>
        <xsl:variable name="sub_before" select="substring-before($file, 'inline')"/>
        <xsl:variable name="sub_after" select="substring-after($file, 'inline')"/>
        <xsl:value-of select="concat($sub_before, 'attachment')"/>
        <xsl:choose>
            <xsl:when test="contains($sub_after, 'inline')">
                <xsl:call-template name="replace">
                    <xsl:with-param name="file" select="$sub_after"/>
                </xsl:call-template>
            </xsl:when>
            <xsl:otherwise>
                <xsl:value-of select="$sub_after"/>
            </xsl:otherwise>
        </xsl:choose>
    </xsl:template> 
</xsl:stylesheet>


您使用的是哪个XSLT处理器?@potame It's Xalan 2.7.1
replace
是2007年引入的XSLT/XPath 2.0中引入的一个函数,并在XSLT 2处理器(如Saxon 9)中实现。您使用的XSLT 1处理器不支持该函数或任何其他XSLT/XPath 2功能。在Java世界中,安装Saxon 9并使用它代替Xalan很容易。@MartinHonnen但这是在XSLT 1中实现的一种方法吗?可以使用递归模板来实现。请参见使用哪个XSLT处理器的示例?@potame It's Xalan 2.7.1
replace
是2007年引入的XSLT/XPath 2.0中引入的一个函数,并在XSLT 2处理器(如Saxon 9)中实现。您使用的XSLT 1处理器不支持该函数或任何其他XSLT/XPath 2功能。在Java世界中,安装Saxon 9并使用它代替Xalan很容易。@MartinHonnen但这是在XSLT 1中实现的一种方法吗?可以使用递归模板来实现。请参阅以获取示例