2014-11-21 3 views
1

У меня есть эта структура в XML:XSL - Проверьте узлы на том же уровне

<report> 
    <text> 
    <chapter>1</chapter> 
    <chapter>2 
     <section>2.1</section> 
    </chapter> 
    <chapter>3</chapter> 
    </text> 
</report> 

В моем ОТД, у меня есть:

<!ELEMENT text (#PCDATA | chapter |section)*> 

Из-за этого, в моем XSL, я хочу убедитесь, что у меня нет chapter и section на том же уровне, перед выполнением преобразования. Таким образом, я не могу иметь этот

<report> 
    <text> 
    <chapter>1</chapter> 
    <chapter>2 
     <section>2.1</section> 
    </chapter> 
    <section>3</section> 
    </text> 
</report> 

Мой XSL

<xsl:template match="chapter"> 

    <div class="chapter"> 
     <h2> 
      <xsl:apply-templates select="chapter-title"/> 
     </h2>  
     <hr/> 
     <xsl:apply-templates select="text() | section "/> 
    </div> 
</xsl:template> 
<xsl:template match="section"> 
    <div class="section"> 
     <h3> 
      <xsl:apply-templates select="section-title"/> 
     </h3> 
     <xsl:apply-templates select="text()"/> 
    </div> 
</xsl:template> 

Как я могу проверить, если раздел и главу находятся на том же уровне, в XSL? Спасибо.

+0

Вы хотите проверить или хотите преобразовать xml в ожидаемый формат xml? –

+0

Я хочу подтвердить. Я просто преобразую раздел, если он не находится на одном уровне главы. @MindPeace я только что редактировал свой пост с моим текущим XSL. – CatCos

ответ

1

После XSLT производит true в качестве своей продукции, если chapter и section не находятся на том же уровне, иначе ничего:

<?xml version="1.0" encoding="UTF-8"?> 
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" version="2.0"> 
<xsl:output method="text" indent="yes" /> 
<xsl:strip-space elements="*"/> 
<xsl:template match="*"> 
    <xsl:choose> 
     <xsl:when test="chapter and section">true</xsl:when> 
     <xsl:otherwise> 
      <xsl:apply-templates select="*"/> 
     </xsl:otherwise> 
    </xsl:choose> 
</xsl:template> 
</xsl:stylesheet> 
+0

Спасибо! Это решило мою проблему. – CatCos

0

Использование осей XPath, родитель должен работать в этом случае:

<xsl:if test="count(parent::*/*) &gt; 0">...</xsl:if> 

Выберите родительский узел: parent::*

Выберите все элементы узлов внутри родительского узла: parent::*/*

сосчитать их и проверьте здесь больше нуля: count(parent::*/*) > 0

* wil l возвращает любой элемент узла, но не текстовый узел. Вы можете использовать имя узла элемента, чтобы выбрать определенные узлы элемента.

+0

Но с этим, как я знаю, что нет главы на том же уровне раздела? Дело в том, что если у меня есть глава на одном уровне раздела, я не могу преобразовать раздел. – CatCos

0

Вам нужно xsl:message:

<xsl:template match="*[chapter][section]"> 
    <xsl:message terminate="yes">There are a section and a chapter on the same level</xsl:message> 
</xsl:template> 

прекратить = "да" пропускает процесс , если процессор приходит к этому сообщению. Если вам просто нужно предупреждение, переключитесь на «нет».

Возможно, Schematron подходит для вас. В этом случае вам понадобится:

<schema xmlns="http://purl.oclc.org/dsdl/schematron" queryBinding="xslt2"> 
    <pattern> 
     <rule context="*[chapter]"> 
      <report test="section">There are a section and a chapter on the same level</report> 
     </rule> 
    </pattern> 
</schema> 
Смежные вопросы