简体   繁体   English

使用XDocument和XmlDocument类从XML文件中删除具有特定节点名称的元素

[英]Delete an element with specific node name from XML file using XDocument and XmlDocument class

I am trying to delete an element with specific node name. 我正在尝试删除具有特定节点名称的元素。 Using the following code but receive an error like "Name cannot begin with the '2' character, hexadecimal value 0x32." 使用以下代码,但会收到类似“名称不能以'2'字符,十六进制值0x32开头”的错误。 As I understand this method is not correct for the relevant xml format. 据我了解,此方法不适用于相关的xml格式。

How can I delete Table with specific User_Name info. 如何删除具有特定User_Name信息的表。 should delete specific table When I try to delete Administrator User 应该删除特定的表当我尝试删除管理员用户时

RemoveElement("Accounts.xml", "User", "Test1");

private static void RemoveElement(string xmlFile, string elementName, string elementAttribute)
    {
        XDocument xDocument = XDocument.Load(xmlFile);
        foreach (var profileElement in xDocument.Descendants("Table").ToList())              
        {
            if (profileElement.Attribute(elementAttribute).Value == elementName) 
            {
                profileElement.Remove();                               
            }
        }
        xDocument.Save(xmlFile);
    }

Here is the Xml file; 这是Xml文件;

`<?xml version="1.0" encoding="utf-8"?>
<Accounts>
  <Table>
    <User>Administrator</User>
    <Domain>Localhost</Domain>
    <Password>Test</Password>
    <Account_Type>Windows</Account_Type>
 </Table>
 <Table>
    <User>Test1</User>
    <Domain>demo</Domain>
    <Password>empty</Password>
    <Account_Type>Domain</Account_Type>
 </Table>
</Accounts>`

Yeah Found it how you can delete when you get info from texBox 是的,发现从texBox获取信息后如何删除它

xDoc.Load("Accounts.xml");
                foreach (XmlNode node in xDoc.SelectNodes("Accounts/Table"))
                {
                    if (node.SelectSingleNode("User").InnerText == textBox1.Text)
                    {
                        node.ParentNode.RemoveChild(node);
                    }

                }
            xDoc.Save("Accounts.xml");

But I Want to get info from listview. 但我想从listview获取信息。 I receive an error When I try to use following code. 尝试使用以下代码时收到错误消息。

Error : InvalidArgument=Value of '0' is not valid for 'index'.\\r\\nParameter name: index 错误:InvalidArgument =值“ 0”对“索引”无效。\\ r \\ n参数名称:索引

listViewMevcutKullaniciListesi.Items.RemoveAt(listViewMevcutKullaniciListesi.SelectedIndices[0]);

xDoc.Load("Accounts.xml");
                foreach (XmlNode node in xDoc.SelectNodes("Accounts/Table"))
                {
                    if (node.SelectSingleNode("User").InnerText == listViewMevcutKullaniciListesi.SelectedIndices[0].ToString())
                    {
                        node.ParentNode.RemoveChild(node);
                    }

                }
            xDoc.Save("Accounts.xml");

Original code snippet doesn't work because name of user is not an attribute of user but a value. 原始代码段无效,因为用户名不是用户的属性而是值。 Also, you can replace .Descendants("Table") with .Descendants(elementName) to avoid unnecessary if statement. 另外,您可以将.Descendants("Table")替换为.Descendants(elementName)以避免不必要的if语句。 I think, the most elegant way to achieve needed functionality is to use Linq to Xml: 我认为,实现所需功能的最优雅方法是使用Linq to Xml:

XDocument xDocument = XDocument.Load(xmlFile);

xDocument.Descendants(elementName)
    .Where(e => e.Value == elementAttribute)
    .ToList()
    .ForEach(e => e.Remove());

xDocument.Save(xmlFile);

As for your second question: I believe that you remove first element in this line 至于您的第二个问题:我相信您会删除此行中的第一个元素

listViewMevcutKullaniciListesi.Items.RemoveAt(listViewMevcutKullaniciListesi.SelectedIndices[0]);

When you call listViewMevcutKullaniciListesi.SelectedIndices[0] for the second time you obviously get an Exception. 当您第二次调用listViewMevcutKullaniciListesi.SelectedIndices[0]时,您显然会获得异常。 Also, listViewMevcutKullaniciListesi.SelectedIndices[0].ToString() don't give you selected item but just it's number. 另外, listViewMevcutKullaniciListesi.SelectedIndices[0].ToString()不会给您选定的项目,而只是给您编号。

Here is the answer with XmlDocument class; 这是XmlDocument类的答案; You are calling the method like 您正在调用类似的方法

`RemoveElementWithXmlDocument("Accounts.xml", "Accounts/Table", "User", listViewMevcutKullaniciListesi.SelectedItems[0].Text);`

method; 方法;

private static void RemoveElementWithXmlDocument(string xmlFile, string nodeName, string elementName, string elementAttribute)
    {
        xDoc.Load(xmlFile);
        try
        {
            foreach (XmlNode node in xDoc.SelectNodes(nodeName))
            {
                if (node.SelectSingleNode(elementName).InnerText == elementAttribute)
                {
                    node.ParentNode.RemoveChild(node);
                }
            }
            xDoc.Save(xmlFile);
        }
        catch (Exception ex)
        {
            MessageBox.Show(ex.Message);
        }
    }

And also I wanna use XDocument class for same structure But I receive an exception like "Object reference not set to an instance of an object" in foreach loop when the ran profileElement.Remove(); 我也想对相同的结构使用XDocument类,但是当运行profileElement.Remove();时,我在foreach循环中收到一个类似“对象引用未设置为对象实例”的异常。 line. 线。 If I comment out to this line never get the exception but I need this line for removing relevant node from xml. 如果我对此行进行注释,则永远不会出现异常,但是我需要此行来从xml中删除相关节点。 So, As I understand I missing something in XDocument. 因此,据我了解,我在XDocument中缺少某些内容。 need your help 需要你的帮助

RemoveElementWithXDocument("Accounts.xml", "Table", "User", listViewMevcutKullaniciListesi.SelectedItems[0].Text);

method for XDocument XDocument的方法

private static void RemoveElementWithXDocument(string xmlFile, string nodeName, string elementName, string elementAttribute)
    {
        XDocument xDocument = XDocument.Load(xmlFile);
        try
        {
            foreach (XElement profileElement in xDocument.Descendants(nodeName))
            {
                if (profileElement.Element(elementName).Value == elementAttribute)
                {
                    profileElement.Remove();
                }
            }
            xDocument.Save(xmlFile);
        }
        catch (Exception ex)
        {
            MessageBox.Show(ex.Message);
        }
    }

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM