【问题标题】:Xml merge using C#使用 C# 进行 XML 合并
【发布时间】:2020-07-11 14:46:30
【问题描述】:
xml1:
<value>
    <Id>1</id>
    <name>AAA</name>
</value>
<value>
    <Id>2</id>
    <name>bbb</name>
</value>
<value>
    <Id>3</id>
    <name>ccc</name>
</value>

xml2:

<value>
<Id>1</id>
<Company>abc</Company>
<address>ASD</address>
</value>

result :
    <value>
        <Id>1</id>
        <name>AAA</name>
        <Company>abc</Company>
        <address>ASD</address>
    </value>
    <value>
        <Id>2</id>
        <name>bbb</name>
    </value>
    <value>
        <Id>3</id>
        <name>ccc</name>
    </value>

如果 1st xml 的 id = 2nd xml 然后将 2nd xml 记录与 1st xml 值记录合并。 在我的代码中,我没有检查 id 值,但我试图将第二个 xml 记录与根与 1xml 记录合并。如果你能帮助我,那就太好了。我收到错误要插入的节点来自不同的文档上下文。

 XmlNode x1 = doc1.SelectSingleNode("/OutLooksync/value");
            foreach (XmlNode node in x1.SelectNodes("/OutLooksync/value"))
            {
                x1.AppendChild(doc2.ImportNode(node, true));

            }
 

【问题讨论】:

    标签: c# xml c#-4.0 linq-to-xml c#-3.0


    【解决方案1】:

    通过使用XmlDocument

    • 您可以在xml1valuesxml2values 中循环
    • 检查id是否等于,并从xml2导入childNodes

    1 - 用于测试的 Xml:

    string xml1 = @"
        <OutLooksync>
            <value>
                <id>1</id>
                <name>AAA</name>
            </value>
            <value>
                <id>2</id>
                <name>bbb</name>
            </value>
            <value>
                <id>3</id>
                <name>ccc</name>
            </value>
        </OutLooksync>";
    
    string xml2 = @"
        <OutLooksync>
            <value>
                <id>1</id>
                <Company>abc</Company>
                <address>ASD</address>
            </value>
        </OutLooksync>";
    

    2 - 导入节点的代码

    XmlDocument xmlDocument1 = new XmlDocument();
    xmlDocument1.LoadXml(xml1);
    
    XmlDocument xmlDocument2 = new XmlDocument();
    xmlDocument2.LoadXml(xml2);
    
    XmlNodeList values1 = xmlDocument1.SelectNodes("/OutLooksync/value");
    XmlNodeList values2 = xmlDocument2.SelectNodes("/OutLooksync/value");
    
    foreach(XmlNode value1 in values1)
    {
        foreach(XmlNode value2 in values2)
        {
            if(value1.SelectSingleNode("./id").InnerText != value2.SelectSingleNode("./id")?.InnerText)
            {
                continue;
            }
            
            foreach(XmlNode toImport in value2.ChildNodes)
            {
                if (toImport.Name == "id")
                    continue;
    
                value1.AppendChild(xmlDocument1.ImportNode(toImport, true));
            }
        }
    }
    
    Console.WriteLine(xmlDocument1.InnerXml);
    

    希望对您有所帮助。

    【讨论】:

    • 我还在努力,我已经对你的代码进行了一些更改,如果它有效,那么我会接受你的回答
    • @MadhavaSM 此代码给出了预期的结果。如果您有任何问题,我会向您解释。代码检查值是否按 id 匹配,因此从 xml2 预期 id 中的值中获取子项并将其放入 xml1 中存在的值中。
    • 它工作正常thnx兄弟。我需要一些小的改变,比如第二个 xml 记录不应该被替换为 1xml 值记录,但它应该显示在它下面,例如.. 1AAA abc
      ASD
      这可能吗??
    • 我能知道你为什么在 if 条件下使用 !=
    • @MadhavaSM 用于 2 个问题:value1.SelectSingleNode("./id").InnerText != value2.SelectSingleNode("./id")?.InnerText 表示:如果 xml 中的值 id 不等于 xml2 中的值 id,则检查 xml2 中的下一个值。对于第 1 个问题,我将添加代码,您不需要代码中的 3 foreach,只需从导入的值中删除 id 到 xml1。
    【解决方案2】:

                string xml1 = @"
        <OutLooksync>
            <value>
                <id>1</id>
                <name>AAA</name>
            </value>
            <value>
                <id>2</id>
                <name>bbb</name>
            </value>
            <value>
                <id>3</id>
                <name>ccc</name>
            </value>
        </OutLooksync>";
    
                string xml2 = @"
        <OutLooksync>
            <value>
                <id>4</id>
                <Company>abc</Company>
                <address>ASD</address>
            </value>
        </OutLooksync>";
                XmlDocument doc1 = new XmlDocument();
                doc1.LoadXml(xml1);
    
                XmlDocument doc2 = new XmlDocument();
                doc2.LoadXml(xml2);
                XmlNode newvalue = doc1.ImportNode(doc2.DocumentElement.FirstChild, true);
                doc1.DocumentElement.AppendChild(newvalue);

    【讨论】:

    • 这段代码有效,但不符合我的逻辑,xml2 的 id 值为 1,因此它应该与 xml1 的 id 值为 1 合并
    • doc1.SelectSingleNode("/OutLooksync/value").AppendChild(newvalue);这个很好用。
    【解决方案3】:

    XmlNodeList x1 = doc1.SelectSingleNodes("/OutLooksync/value");
        foreach (XmlNode node in x1)
            {
                doc2.appendChild(node);
    
             }

    【讨论】:

    • 我收到错误无法将 xmlnode 隐式转换为 xmlnodelist。如果我使用 xmlnode,那么我获取要插入的节点来自不同的文档上下文。
    • doc2.SelectSingleNode("/OutLooksync").appendChild(node);
    • 对象引用错误兄弟
    • @MadhavaSM 用 4 行代码做到这一点并不简单
    猜你喜欢
    • 2017-01-11
    • 2023-03-25
    • 1970-01-01
    • 1970-01-01
    • 2020-12-25
    • 2014-03-09
    • 2016-01-29
    • 1970-01-01
    • 2021-08-01
    相关资源
    最近更新 更多