Dim*_*hev 10
人们经常可以找到漂亮的XSLT代码的例子,特别是当XSLT用作函数式编程语言时.
有关示例,请参阅有关FXSL 2.0的文章 - XSLT 2.0的函数编程库.
作为FP语言,XSLT也是一种声明性语言.除其他外,这意味着一个人声明,指定现有的关系.
这样的定义通常不需要任何额外的代码来产生结果 - 它本身就是它自己的实现,或者是可执行的定义或可执行的规范.
这是一个小例子.
此XPath 2.0表达式定义 " 自然数的最大素数因子 ":
if(f:isPrime($pNum))
then $pNum
else
for $vEnd in xs:integer(floor(f:sqrt($pNum, 0.1E0))),
$vDiv1 in (2 to $vEnd)[$pNum mod . = 0][1],
$vDiv2 in $pNum idiv $vDiv1
return
max((f:maxPrimeFactor($vDiv1),f:maxPrimeFactor($vDiv2)))
Run Code Online (Sandbox Code Playgroud)
,它的发音在英文,数字的最大素因子pNum是数字本身,如果 pNum 是素数,否则,如果 vDiv1和vDiv2是两个因素pNum,则最大素因子pNum是最大素因子的大vDiv1和vDiv2.
我们如何使用它来实际计算 XSLT中的最大素数因子?我们简单地将上面的定义包含在<xsl:function>...中...得到结果!
<xsl:function name="f:maxPrimeFactor" as="xs:integer">
<xsl:param name="pNum" as="xs:integer"/>
<xsl:sequence select=
"if(f:isPrime($pNum))
then $pNum
else
for $vEnd in xs:integer(floor(f:sqrt($pNum, 0.1E0))),
$vDiv1 in (2 to $vEnd)[$pNum mod . = 0][1],
$vDiv2 in $pNum idiv $vDiv1
return
max((f:maxPrimeFactor($vDiv1),f:maxPrimeFactor($vDiv2)))
"/>
</xsl:function>
Run Code Online (Sandbox Code Playgroud)
然后,我们可以计算任何自然数的MPF,例如:
f:maxPrimeFactor(600851475143) = 6857
至于效率,这个转换只需0.109秒.
优雅和高效的XSLT代码的其他示例:
以下是编写"高质量XSLT代码"的一些规则,取自Mukul Ghandi的博客.
DontUseDoubleSlashOperatorNearRoot:避免在大树的根附近使用运算符.
DontUseDoubleSlashOperator:避免在XPath表达式中使用运算符//.
SettingValueOfVariableIncorrectly:如果指定字符串值,则使用'select'语法为变量赋值.
EmptyContentInInstructions:不要将空内容用于'xsl:for-each''xsl:if''xsl:when'等指令.
DontUseNodeSetExtension:如果使用XSLT 2.0,请不要使用节点集扩展功能.
RedundantNamespaceDeclarations:xsl:stylesheet元素中有冗余的名称空间声明.
UnusedFunction:样式表函数未使用.
UnusedNamedTemplate:样式表中的命名模板未使用.
UnusedVariable:样式表中未使用变量.
UnusedFunctionTemplateParameter:函数/模板体中未使用函数或模板参数.
TooManySmallTemplates:样式表中有太多低粒度模板(10个或更多).
MonolithicDesign:在样式表中使用单个模板/函数.您可以模块化代码.
OutputMethodXml:生成HTML代码时使用输出方法'xml'.
NotUsingSchemaTypes:在XSLT 2.0模式下工作时,样式表没有使用任何内置的Schema类型(xs:string等).
UsingNameOrLocalNameFunction:当local-name()适当时使用name()函数(反之亦然).
FunctionTemplateComplexity:函数或模板的大小/复杂度很高.需要重构代码.
NullOutputFromStylesheet:样式表没有生成任何有用的输出.请查看样式表逻辑.
UsingNamespaceAxis:使用不推荐使用的命名空间轴,在XSLT 2.0模式下工作.
CanUseAbbreviatedAxisSpecifier:使用像child ::,attribute ::或parent :: node()这样的冗长轴说明符.
UsingDisableOutputEscaping:已将disable-output-escaping属性设置为"yes".请查看样式表逻辑.
NotCreatingElementCorrectly:直接使用xsl:element指令创建元素节点.
AreYouConfusingVariableAndNode:您可能会将变量引用与节点引用混淆.(由Alain Benedetti提供)
IncorrectUseOfBooleanConstants:错误地将布尔常量用作'true'或'false'.(由Tony Lavinio提供)
ShortNames:为变量/ function/template使用单个字符名称.为这些功能使用有意义的名称.
NameStartsWithNumeric:变量/函数/模板名称以数字字符开头
最佳实践1:尽可能使用模板而不是<xsl:for-each>(99%的情况)
(我可以在最佳实践中添加MAINTAINABILITY作为额外成分,即使是最重要的实践也是如此)
为了理解xsl,你真的需要一些练习.
不明白什么...... 当然,做的很亲戚.
这对于XSLT来说是双重的,因为xsl:for-each构造往往是
对于一个新手,但事实上
比模板,只有
永远不要使用<xsl:for-each>元素!
我承认,标题有点夸张,确实存在,我被告知,"xsl for each"可以有它的优点,但这些情况非常非常罕见.
我曾经不得不在不到一周的时间内找到一个相当复杂的xml/xslt客户端站点,并在整个地方使用了for-each元素.现在,几年后,我更加聪明,我花了很多时间重新编写初始代码,仅使用模板.现在代码更清晰,更具适应性.
要么你知道这个,要么你应该:<xsl:template>和<xsl:apply-templates>几乎总是要走的路.如果你是xsl-ing,并且你没有完全理解这些标签,那么现在就停止工作,学习它们,得到一个aha-erlebnis,并继续你的工作作为一个重生(wo)男人.
我认为,回答这个问题的一种好方法是从另一侧着手解决。哪些做法使XSLT 无效,为什么?
我所看到的一些情况导致XSLT无效:
过度使用for-each。 每个人都这么说;我再说一遍。我发现这for-each通常是开发人员尝试以声明性语言使用传统编程技术的标志。
未充分利用XPath。 我看到的许多不良XSLT纯粹是因为开发人员不了解谓词,轴说明符position()和current(),所以他改为使用XSLT构造实现了逻辑。
未充分利用元数据。通过为您的转换提供元数据, 有时可以消除大量 XSLT。
未充分利用预处理。 例如,如果XML文档包含必须使用XSLT字符串操作进行解析的数据,则在XSLT之外进行所有解析并将解析后的结果添加到XML或将解析后的结果作为参数传递通常要容易得多。进行转换。我已经看到了一些非常难以维护的XSLT实现业务逻辑,这些逻辑在C#或Python中实现起来很简单。
我在自己的XSLT世界中遇到的最大问题(我正在维护3000多个行转换)是无效代码。我确定我的转换中有一些模板将不再使用,因为它们正在测试的条件将不会再出现。无法以编程方式确定类似的东西<xsl:template match="SomeField[contains(., "some value")]>是存在还是死亡,因为它取决于元数据无法告诉您的东西。
| 归档时间: |
|
| 查看次数: |
3520 次 |
| 最近记录: |