2016-08-08 2 views
1

Я создаю XDocument с пространствами имен в моем конструкторе, например.Добавить XElement, который использует пространство имен

this.nsXsl = XNamespace.Get("http://www.w3.org/1999/XSL/Transform"); 
this.doc = new XDocument(
       new XElement(nsXsl + "stylesheet", new XAttribute("version", "1.0"), new XAttribute(XNamespace.Xmlns + "xsl", "http://www.w3.org/1999/XSL/Transform"), 
       new XElement(nsXsl + "output", new XAttribute("method", "xml"), new XAttribute("indent", "yes"), new XAttribute("encoding", "UTF-8")), 
       new XElement(nsXsl + "strip-space", new XAttribute("elements", "*"))) 
       ); 

Этот документ имеет правильную структуру и выглядит так, как будто я хочу.

Но у меня есть функция, как:

private XElement createTemplate(string match, string node, string fork, string select) 
     { 
      return new XElement(this.nsXsl + "template", new XAttribute("match", match), new XElement(node, 
       new XElement(this.nsXsl + fork, new XAttribute("select", select)))); 

     } 

эта функция возвращает XElement следующей структуры:

<template match="/shiporder/shipto" xmlns="http://www.w3.org/1999/XSL/Transform"> 
    <Line1> 
    <apply-templates select="city" xmlns="" /> 
    </Line1> 
</template> 

Но мне нужен XElement как:

<xsl:template match="/shiporder/shipto"> 
    <Line1> 
    <xsl:apply-templates select="city" /> 
    </Line1> 
</xsl:template> 
+0

Изменения вы хотите только косметический, и как/когда новый XElement прилагаются к XDoc? –

+0

@HenkHolterman до сих пор у меня есть список шаблонов и добавлю их как 'foreach (XElement elem в шаблонах) { doc.Add (elem); } ' – StellaMaris

+1

Тогда проблема разрешится сама. Не делай ничего. –

ответ

1

Там это две точки. Во-первых, ваш элемент Line1 имеет пространство имен, а apply-templates - нет, а то, что вы хотите, - наоборот. Это ваше собственное дело: вы добавляете пространство имен в new XElement(this.nsXsl + node, … (node, я полагаю, это "Line1"), и вы опускаете это в new XElement(fork, … (очевидно, fork - "apply-templates"). Просто переместите this.nsXsl + от прежнего до последнего места.

Во-вторых, вы говорите, что предпочтете, чтобы пространство имен XSLT было обозначено префиксом, xsl. Связывание между префиксом и пространством имен задается объявлением, выраженным в виде атрибута специальной формы, new XAttribute(XNamespace.Xmlns + prefix, namespaceUri) (вы на самом деле делаете это в своем первом фрагменте кода). Эта привязка действительна в элементе, где он объявлен, и всем вложенным элементам, если они не перекрываются другим объявлением. Когда XML-писатель испускает элемент с именем с именем пространства имен, он обнаруживает, что это пространство имен привязано к префиксу и использует этот префикс (например, в вашем первом фрагменте кода, пространство имен http://www.w3.org/1999/XSL/Transform привязано к префиксу xsl, поэтому разработчик XML добавляет xsl: префикс для всех вложенных элементов). Если писатель XML обнаруживает, что используемое пространство имен не привязано к префиксу, оно выдает атрибут объявления пространства имен по умолчанию, xmlns="namespace" (обратите внимание, что пространство имен по умолчанию влияет только на элементы, а не на атрибуты).

С точки зрения информационной модели XML, следующие три фрагмента текста эквивалентен:

<template match="/shiporder/shipto" xmlns="http://www.w3.org/1999/XSL/Transform"> 
    <Line1 xmlns=""> 
    <apply-templates select="city" xmlns="http://www.w3.org/1999/XSL/Transform" /> 
    </Line1> 
</template> 

<xsl:template match="/shiporder/shipto" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"> 
    <Line1> 
    <xsl:apply-templates select="city" /> 
    </Line1> 
</template> 

<weird:template match="/shiporder/shipto" xmlns:weird="http://www.w3.org/1999/XSL/Transform"> 
    <Line1> 
    <weird:apply-templates select="city" /> 
    </Line1> 
</template> 
+0

Согласен в первом пункте. Во второй момент, о котором вы упоминали добавить «xsl:» перед моими именами тегов, возможно только добавление нового XAttribute (XNamespace.Xmlns + prefix, namespaceUri) к моему XElement? – StellaMaris

+0

@StellaMaris, точно. Так же, как это было сделано в вашем первом фрагменте кода. – ach

+0

Можно ли использовать 'XName nodeName = this.nsXsl +" template "; XElemnet e = this.doc.Element (nodeName); 'some how? – StellaMaris

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