2016-07-14 11 views
0

Мне нужно преобразовать XML в XHTML. В XML есть несколько абзацев и вложенные цитаты, например.Преобразование XML в XHTML

<para>SomeText</para> 
<para><quote>SomeText</quote></para> 
<para>SomeText</para> 

Я попытался это:

<xsl:choose> 
    <xsl:when test="//text/para"> 
     <xsl:for-each select="//text"> 
      <xsl:for-each select="//para"> 
       <p><xsl:value-of select="text()"/></p> 
      </xsl:for-each> 
     </xsl:for-each> 
    </xsl:when> 
    <xsl:when test="//text/para[quote]"> 
     <xsl:for-each select="//text"> 
      <xsl:for-each select="//para/quote"> 
       <p><q><xsl:value-of select="text()"/></q></p> 
      </xsl:for-each> 
     </xsl:for-each> 
    </xsl:when> 
</xsl:choose> 

Второе условие просто игнорируется, однако.

+0

Вы должны сделать некоторые серьезное чтение, прежде чем делать какие-либо более кодирования. Прочитайте правила шаблонов, динамический контекст XPath и значение «//» в начале выражения пути. –

ответ

2

Как @LarsH указывает, избегайте <xsl:for-each>. Используйте сопоставление шаблонов.

Это простое преобразование:

<xsl:transform version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"> 

    <xsl:template match="para"> 
    <p><xsl:apply-templates /></p> 
    </xsl:template> 

    <xsl:template match="quote"> 
    <q><xsl:apply-templates /></q> 
    </xsl:template> 

</xsl:transform> 

превратит это:

<text> 
    <para>SomeText</para> 
    <para><quote>SomeText</quote></para> 
    <para>SomeText</para> 
</text> 

в

<p>SomeText</p> 
<p><q>SomeText</q></p> 
<p>SomeText</p> 

Дальнейшее чтение здесь на SO:

+0

Большое спасибо. Но у меня есть шаблон, который соответствует корню в верхней части заголовка, метаданных и т. Д. Если я сейчас вставляю эти два шаблона под ним, я получаю эту ошибку: «Элемент должен использоваться только на верхнем уровне таблицы стилей». – Fajeth88

+0

Вы не можете вложить '' (который является синонимом ''). Переместите два шаблона самостоятельно. Кроме того, скорее всего, они никогда не будут выполняться до тех пор, пока вы не добавите шаблон '' где-нибудь в главном шаблоне. Как и Ларс, я сначала рекомендую сначала прочитать «». Ссылка в его комментарии и первая ссылка в моем ответе содержат введение. – Tomalak

+0

Хорошо, я сделаю это. – Fajeth88

1

Проблема заключается в том, что вы используете выражения XPath, которые игнорируют контекст (кроме контекстного документа), то есть выражения, начинающиеся с //. Поэтому, если у вас есть элемент <para> в любом месте документа с дочерним элементом <quote>, первое условие всегда будет истинным, а второе условие никогда не будет достигнуто.

Действительно, вы хотите переместить для каждого цикла (или, вероятно, лучше, набор шаблонов с шаблонами совпадений и шаблонов применений) вне условий выбора/когда. Фактически вам, вероятно, не понадобится выбрать/когда вообще, как только у вас появятся правильные шаблоны.

(заселение некоторую информацию от комментариев)

XSLT и XPath являются достаточно сложными, что это действительно стоит изучить основы, прежде чем пытаться получить что-то работает методом проб и ошибок. Вы сэкономите много времени. Для общего введения я бы рекомендовал

Тогда для более продвинутой обсуждения xsl:for-each VS. xsl:apply-templates см

+0

Thx, я попробую. После того, как я выясню, как это все равно - это первый раз, когда я работаю с XML/HTML. – Fajeth88

+1

@ Fajeth88: На самом деле стоит изучить основы, прежде чем делать много проб и ошибок. XSLT/XPath достаточно сложны, даже если вы их понимаете. После того, как вы прочитали учебное пособие по каждому из вариантов шаблонов заявок, попробуйте http://stackoverflow.com/questions/4460232/differences-between-for-each-and-templates-in-xsl – LarsH