Как выбрать элементы по части их имени в XSL / XPath? - PullRequest
6 голосов
/ 14 февраля 2012

Как использовать apply-templates для выбора только тех элементов по имени (не по значению), которые заканчиваются конкретным шаблоном?Предположим, что следующий xml ...

<report>
  <report_item>
    <report_created_on/>
    <report_cross_ref/>
    <monthly_adj/>
    <quarterly_adj/>
    <ytd_adj/>
  </report_item>
  <report_item>
   ....
  </report_item>
</report>

Я хочу использовать <xsl:apply-templates> на всех экземплярах <report_item>, где элементы-потомки заканчиваются на 'adj`, поэтому в этом случае только month_adj, quaterly_adj,и ytd_adj будет выбран и применен с шаблоном.

<xsl:template match="report">
   <xsl:apply-templates select="report_item/(elements ending with 'adj')"/>
</xsl:template>

Ответы [ 2 ]

10 голосов
/ 14 февраля 2012

Я не думаю, что синтаксис регулярного выражения доступен в этом контексте, даже в XSLT 2.0. Но вам это не нужно в этом случае.

<xsl:apply-templates select="report_item/*[ends-with(name(), 'adj')]"/>

* соответствует любому узлу

[pred] выполняет проверку узла по селектору (в данном случае *) (где pred - предикат, вычисленный в контексте выбранного узла)

name() возвращает имя тега элемента (для этой цели должно быть эквивалентно local-name).

ends-with() - встроенная строковая функция XPath.

2 голосов
/ 14 февраля 2012

Слегка аккуратное решение (только XSLT 2.0+):

<xsl:apply-templates select="report_item/*[matches(name(),'adj$')]"/>

Вот самопроверка, чтобы доказать, что это работает. (Проверено на саксонском языке).

<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<xsl:stylesheet version="2.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
                xmlns:fn="http://www.w3.org/2005/xpath-functions" 
                xmlns:xs="http://www.w3.org/2001/XMLSchema" 
                exclude-result-prefixes="xs fn">
 <xsl:output method="xml" indent="yes" encoding="utf-8" />
 <xsl:variable name="report-data">
  <report>
   <report_item>
     <report_created_on/>
     <report_cross_ref/>
     <monthly_adj>Jan</monthly_adj>
     <quarterly_adj>Q1</quarterly_adj>
     <ytd_adj>2012</ytd_adj>
   </report_item>
  </report>
 </xsl:variable>
 <xsl:template match="/" name="main">
  <reports-ending-with-adj>
   <xsl:element name="using-regex">
    <xsl:apply-templates select="$report-data//report_item/*[fn:matches(name(),'adj$')]"/> 
   </xsl:element>
   <xsl:element name="using-ends-with-function">
    <xsl:apply-templates select="$report-data//report_item/*[fn:ends-with(name(), 'adj')]"/>
   </xsl:element>
  </reports-ending-with-adj>
 </xsl:template>
</xsl:stylesheet>
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...