2013-03-15 3 views
1

Я хочу удалить нежелательный контент из некоторых элементов списка в моем html. В основном я хочу разделить весь контент до определенного диапазона (с вкладкой класса), но только если контент до этого диапазона соответствует некоторым критериям.xslt2 удалить указанную часть из узла

Возьмем, например, пример ниже:

<ol class="ast"> 
    <li>*<span class="tab"><!--tab--></span>Some blabla <img href="#">with a link.</a></li> 
    <li>**<span class="tab"><!--tab--></span>Some other blabla, this one without other elements</li> 
</ol> 

То, что я хотел бы получить следующий:

<ol class="ast"> 
    <li>Some blabla <img href="#">with a link.</a></li> 
    <li>Some other blabla, this one without other elements</li> 
</ol> 

или объяснить словами, если у меня есть элемент списка, начиная с одного или больше звездочки, за которым следует промежуток вкладок, а затем сохраняйте только контент после пролета.

Я немного обманывал, но не смог найти что-то, удовлетворяющее мои потребности, поэтому любые советы снова приветствуются!

ответ

0

Принятая в настоящее время решение является некорректным и обычно приводит к получению неверных результатов , Например, при нанесении на этом XML-файле:

<ol class="ast"> 
    <li><a href="#">with a link.</a>*<span class="tab">Some blabla </span></li> 
    <li>Something else</li> 
</ol> 

это неверный результат (span и текст неправильно удалены) производится:

<?xml version="1.0" encoding="UTF-8"?><ol class="ast"> 
    <li><a href="#">with a link.</a></li> 
    <li>Something else</li> 
</ol> 

Вот один правильное решение:

<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"> 
<xsl:output omit-xml-declaration="yes" indent="yes"/> 
<xsl:strip-space elements="*"/> 

<xsl:template match="node()|@*"> 
    <xsl:copy> 
    <xsl:apply-templates select="node()|@*"/> 
    </xsl:copy> 
</xsl:template> 

<xsl:template match= 
    "li/node()[1] 
    [self::text() and not(translate(.,'*','')) 
    and following-sibling::node()[self::span[@class='tab']] 
    ]"/> 

<xsl:template match= 
    "li/node()[2] 
     [self::span[@class='tab'] 
    and preceding-sibling::node()[1] 
      [self::text() and not(translate(.,'*',''))] 
     ] 
"/> 
</xsl:stylesheet> 

При нанесении на поставленном XML документа:

<ol class="ast"> 
    <li>*<span class="tab"><!--tab--></span>Some blabla <a href="#">with a link.</a></li> 
    <li>Not asterisks!<span class="tab"><!--tab--></span>Some other blabla, this one without other elements</li> 
    <li>**<span class="tab"><!--tab--></span>Some other blabla, this one without other elements</li> 
    <li>***<span>hello</span>Some other blabla, this one without other elements</li> 
</ol> 

это преобразование производит разыскиваемого, правильный результат:

<ol class="ast"> 
    <li>*<span class="tab"><!--tab--></span>Some blabla <a href="#">with a link.</a></li> 
    <li>Not asterisks!<span class="tab"><!--tab--></span>Some other blabla, this one without other elements</li> 
    <li>**<span class="tab"><!--tab--></span>Some other blabla, this one without other elements</li> 
    <li>***<span>hello</span>Some other blabla, this one without other elements</li> 
</ol> 

При нанесении на первый документ XML выше:

<ol class="ast"> 
    <li><a href="#">with a link.</a>*<span class="tab">Some blabla </span> 
    </li> 
    <li>Something else</li> 
</ol> 

снова правильный результат произведено:

<ol class="ast"> 
    <li> 
     <a href="#">with a link.</a>*<span class="tab">Some blabla </span> 
    </li> 
    <li>Something else</li> 
</ol> 
0

Как это:

<xsl:stylesheet 
    xmlns:xs="http://www.w3.org/2001/XMLSchema" 
    xmlns:xsl="http://www.w3.org/1999/XSL/Transform" version="2.0" 
    exclude-result-prefixes="xs"> 

    <xsl:template match="@*|node()"> 
    <xsl:copy> 
     <xsl:apply-templates select="@*|node()"/> 
    </xsl:copy> 
    </xsl:template> 
    <xsl:template match="li/node()[1] 
            [self::text() and 
            matches(., '^\*+$') and 
            following-sibling::node()[1] 
              [self::span and @class = 'tab'] 
            ]" /> 
    <xsl:template match="li/node()[2] 
            [self::span and @class = 'tab'] 
            [matches(preceding-sibling::text(), '^\*+$')]" /> 

</xsl:stylesheet> 

При запуске на этом входе:

<ol class="ast"> 
    <li>*<span class="tab"><!--tab--></span>Some blabla <a href="#">with a link.</a></li> 
    <li>Not asterisks!<span class="tab"><!--tab--></span>Some other blabla, this one without other elements</li> 
    <li>**<span class="tab"><!--tab--></span>Some other blabla, this one without other elements</li> 
    <li>***<span>hello</span>Some other blabla, this one without other elements</li> 
    <li><a href="#">with a link.</a>*<span class="tab">Some blabla </span></li> 
</ol> 

Результат является:

<ol class="ast"> 
    <li>Some blabla <a href="#">with a link.</a></li> 
    <li>Not asterisks!<span class="tab"/>Some other blabla, this one without other elements</li> 
    <li>Some other blabla, this one without other elements</li> 
    <li>***<span>hello</span>Some other blabla, this one without other elements</li> 
    <li><a href="#">with a link.</a>*<span class="tab">Some blabla </span></li> 
</ol> 
+0

отлично, спасибо большое! – Wokoman

+1

Работает на этом входе, но из заявления о прозаической проблеме я бы использовал следующий-sibling :: * [1] [self :: span], а не следующий-sibling :: span, и аналогично для предыдущего-брата. Однако я, возможно, неправильно истолковал требования - я часто это делаю. –

+0

Я понимаю, что есть ситуации, когда решение может не работать, но в структуре моих документов было бы хорошо, хотя и с возможностью улучшения.Просто заявляя, что, возможно, немного сложно проголосовать, поскольку по сути решение было правильным для данной проблемы. – Wokoman

Смежные вопросы