Удалить один элемент при преобразовании, если найдены два одинаковых элемента - PullRequest
1 голос
/ 19 октября 2011

Я преобразую несколько документов одновременно, используя XSLT.Эти документы могут иметь такие элементы, как <a:updated></a:updated> или <app:edited></app:edited>, а некоторые из них имеют как <a:updated></a:updated>, так и <app:edited></app:edited>.

В этом случае некоторые из выданных документов (помимо стандартных элементов, таких как заголовок, ссылка, content) имеют два элемента <posted></posted>.

Вопрос в том, как мне удалить один элемент <posted></posted>, если <app:edited> и <a:updated> находятся в одном и том же <entry></entry>?

Это заголовок XSLT

<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"  xmlns:a="http://www.w3.org/2005/Atom" xmlns:app="http://www.w3.org/2007/app">

Это шаблон

<xsl:template match="a:updated | app:edited">
  <posted>    
    <xsl:apply-templates select="node() | @*" />
  </posted>
</xsl:template>

, вот как я его обрабатываю

$xproc = new XsltProcessor();
$xslt = new DomDocument;
$xslt->load('stylesheet.xslt');
$xproc->importStylesheet($xslt);

, и этов основном XML

<entry>
<id></id>
<title></title>
<content></content>
<link></link>
<a:updated></a:updated>
<app:edited></app:edited>
</entry> 

1 Ответ

0 голосов
/ 19 октября 2011

Правильный ответ зависит от исходного XML-документа, который вы не показали.

В общем, как и какой шаблон вообще выбран для выполнения, зависит от инструкции <xsl:apply-templates>, которая выбирает этот шаблонпоэтому попробуйте что-то вроде этого:

<xsl:apply-templates select=
  "(//*
     [self::a:updated 
     or 
      self::updated 
     or self::app:edited
     ]) 
      [1]
"/>

Если возможно, попробуйте заменить приведенный выше псевдо-оператор // более конкретным выражением XPath, поскольку // печально известен своей неэффективной природой.

Обновление : Теперь, когда ОП опубликовал документ XML, вот более конкретное решение:

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

 <xsl:template match="/">
    <xsl:apply-templates select=
      "(/*/*
         [self::a:updated
         or
          self::updated
         or self::app:edited
         ])
          [1]
    "/>
 </xsl:template>

 <xsl:template match="a:updated | app:edited">
      <posted>
        <xsl:apply-templates select="node() | @*" />
      </posted>
 </xsl:template>
</xsl:stylesheet>

Когда это преобразование применяется к предоставленномуXML-документ (массируется, чтобы он был правильно сформирован):

<entry xmlns:a="a" xmlns:app="app">
    <id></id>
    <title></title>
    <content></content>
    <link></link>
    <a:updated></a:updated>
    <app:edited></app:edited>
</entry>

требуемый правильный результат (<posted> встречается только один раз в выходных данных) * Производится :

<posted/>
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...