代码之家  ›  专栏  ›  技术社区  ›  Daniel Plaisted

如何将LINQ中的元素深度复制到XML?

  •  60
  • Daniel Plaisted  · 技术社区  · 16 年前

    我想制作LINQ到XML元素的深度副本。我之所以要这样做,是因为文档中有一些节点,我想创建它们的修改副本(在同一文档中)。我看不出有什么方法可以做到这一点。

    5 回复  |  直到 15 年前
        1
  •  148
  •   TheCloudlessSky    13 年前

    XElement original = new XElement("original");
    XElement deepCopy = new XElement(original);
    

    [TestMethod]
    public void XElementShallowCopyShouldOnlyCopyReference()
    {
        XElement original = new XElement("original");
        XElement shallowCopy = original;
        shallowCopy.Name = "copy";
        Assert.AreEqual("copy", original.Name);
    }
    
    [TestMethod]
    public void ShouldGetXElementDeepCopyUsingConstructorArgument()
    {
        XElement original = new XElement("original");
        XElement deepCopy = new XElement(original);
        deepCopy.Name = "copy";
        Assert.AreEqual("original", original.Name);
        Assert.AreEqual("copy", deepCopy.Name);
    }
    
        2
  •  9
  •   Daniel Plaisted    16 年前

    看起来ToString和Repasse方法是最好的方法。代码如下:

    XElement copy = XElement.Parse(original.ToString());
    
        3
  •  4
  •   Wonko    16 年前

    直接从 C# 3.0 in a Nutshell :

    将节点或属性添加到元素时(无论是通过函数构造还是添加方法),节点或属性的父属性将设置为该元素。节点只能有一个父元素:如果向第二个父节点添加已为父节点的节点,则该节点将自动进行深度克隆。在以下示例中,每个客户都有一份单独的地址副本:

    var address = new XElement ("address",
                      new XElement ("street", "Lawley St"),
                      new XElement ("town", "North Beach")
                  );
    var customer1 = new XElement ("customer1", address);
    var customer2 = new XElement ("customer2", address);
    
    customer1.Element ("address").Element ("street").Value = "Another St";
    Console.WriteLine (
      customer2.Element ("address").Element ("street").Value);   // Lawley St
    

    这种自动复制使X-DOM对象实例化不受函数编程的其他特征的影响。

        4
  •  -1
  •   pb2q    11 年前

    这应该起作用:

    var copy = new XElement(original.Name, original.Attributes(),
                            original.Elements() );
    
        5
  •  -3
  •   JaredPar    16 年前

    1. 用访客模式写在自己身上

    访问者模式当然是可能的,但它需要大量的工作和测试。我认为你最好的选择是#1。