【问题标题】:How to save multiple Entries to xml through Serialization in c#如何通过C#中的序列化将多个条目保存到xml
【发布时间】:2021-03-16 17:20:42
【问题描述】:

我有一个作为学校任务的 c# 应用程序,我必须能够使用序列化将数据保存到 xml。到目前为止,我能够保存一个类的实例,例如 Customer。但是当我输入新数据时,旧数据被覆盖,只有一个数据可用。有人可以看看我的代码并告诉我哪里错了吗?

serializationClass 这里是我序列化或反序列化我的 xml 的方法:

namespace Aufgabe_1
{
    class serializerHelper
    {
        public void XmlSerialize(Type data, object objectData, string fileName)
        {
            using (var fileStream = new FileStream(fileName, FileMode.Append)) 
            {
                XmlSerializer xSerializer = new XmlSerializer(data);
                xSerializer.Serialize(fileStream, objectData);
            }
        
        }

        public object showData(Type dataType, string fileName)
        {
            object obj;
           
          XmlSerializer xSerializer2 = new XmlSerializer(dataType);

            TextReader textReader = new StreamReader(fileName);
            obj = xSerializer2.Deserialize(textReader);

            return obj;
        
        }
        }

我尝试将数据保存到 xml 的班级:

namespace Aufgabe_1
{
    [Serializable]
    public class Kunde
    {
        public string firstName;
        public string lastName;
        public string adress;
        public string birthday;
        public string bankDetails;

        public Kunde() { }
       

       public Kunde(string firstname, string lastname, string adress, string birthday, string bankdetails)
       
       {
         this.firstName = firstname;
           this.lastName = lastname;
            this.adress = adress;
            this.birthday = birthday;
           this.bankDetails = bankdetails;

        }

        public  bool saveCustomer()
        {
            Console.Clear();
            Console.WriteLine("Bitte geben sie den Namen des Kunden ein!");
           string firstNameInput = Console.ReadLine();
            Console.WriteLine("Bitte geben sie den Nachnamen des Kunden ein!");
            string lastNameInput = Console.ReadLine();
            Console.WriteLine("Bitte geben sie den Adresse des Kunden ein!");
            string adressInput =  Console.ReadLine();
            Console.WriteLine("Bitte geben sie den Geburtsdatum des Kunden ein!");
            string birthdayInput = Console.ReadLine();
            Console.WriteLine("Bitte geben sie den Bankdetails des Kunden ein!");
            string bankDetailsInput = Console.ReadLine();

            Kunde customer = new Kunde(firstNameInput, lastNameInput, adressInput, birthdayInput, bankDetailsInput);
            Console.Clear();

           string filePath = "customerDatabase2.xml";
        serializerHelper sHelper = new serializerHelper();
        if (File.Exists("customerDatabase2.xml"))
        {
            kList = sHelper.showData(typeof(List<Kunde>), filePath) as List<Kunde>;

        }

        kList.Add(customer);

        sHelper.XmlSerialize(typeof(List<Kunde>), kList, filePath);
        Console.WriteLine("Ihr Kunde wurde gespeichert danke für die Zusammenarbeit!");

        Console.Clear();
        Console.WriteLine("Drücken Sie 1 um ins Hauptmenü zu gelangen und auf 2 um die Applikation zu beenden!");
        Program p = new Program();


            switch (Console.ReadLine())
            {
                case "1": Program.menuPoints(); return true;
                case "2": Environment.Exit(0); return true;
               
            }
            return true;
        }


        public void showCustomers()
        {
            Console.Clear();
            Console.WriteLine("Hier sind Ihre Kunden!");

            string filePath = "customerDatabase.xml";
            serializerHelper sHelper = new serializerHelper();
            Kunde k;
           k = sHelper.showData(typeof(Kunde),filePath) as Kunde;
            Console.WriteLine("Vorname" + "Nachname" + "Adresse" + "Geburtsdatum" + "Bankdaten");
           Console.WriteLine(k.firstName + k.lastName + k.adress + k.birthday + k.bankDetails);
        }
    }
}

我尝试使用 .Append 而不是 FileMode.Create,这样我可以保存 Kunde 类的多个实例,但随后我的 xml 中出现错误,无法再对其进行反序列化。

【问题讨论】:

  • 你需要添加一个包含昆德语列表的根类。公共类 Root { public List Kundes { get;set;}}
  • 我必须在我当前的班级内还是作为单独的班级这样做?我的意思是根类
  • 一个单独的类。使用新类和改变类型:sHelper.showData(typeof(Kundes),filePath) as Kundes;

标签: c# .net xml


【解决方案1】:

建议您保留.Create 并读/写Kunde 实例列表,而不是使用.Append。在您阅读列表并添加到列表的位置以及保存时,您保存了整个列表。

因此,为了与您的帖子的布局保持一致,您可以尝试以下方式:

            Kunde customer = new Kunde(firstNameInput, lastNameInput, adressInput, birthdayInput, bankDetailsInput);
            Console.Clear();

            string filePath = "customerDatabase.xml";
            serializerHelper sHelper = new serializerHelper();
            // This is assuming you have a valid file to begin with
            List<Kunde> kList = sHelper.showData(typeof(List<Kunde>),filePath) as List<Kunde>;
            kList.Add(customer);

            sHelper.XmlSerialize(typeof(List<Kunde>), kList, filePath);
            Console.WriteLine("Ihr Kunde wurde gespeichert danke für die Zusammenarbeit!");

在你的 showCustomers() 中,类似这样的内容:

            serializerHelper sHelper = new serializerHelper();
            List<Kunde> kList = sHelper.showData(typeof(List<Kunde>),filePath) as List<Kunde>;
            foreach(var k in kList)
            {
                Console.WriteLine("Vorname" + "Nachname" + "Adresse" + "Geburtsdatum" + "Bankdaten");
                Console.WriteLine(k.firstName + k.lastName + k.adress + k.birthday + k.bankDetails);
            }

【讨论】:

  • 嗨,我尝试了您的解决方案,但是当我尝试添加另一个解决方案时,我收到此错误:该进程无法访问“customerDatabase2.xml”,因为它正在被另一个进程使用。但是我关闭并重新打开了应用程序,仍然是同样的错误。我编辑了我的代码来实现你的方法
  • 在互联网上它说我必须关闭我尝试过的流,但仍然没有运气。如果我把 if 部分拿走,它就可以工作。但随后 xml 再次被覆盖。
  • 确保关闭showData 中的文件,例如,在TextReader... 周围放置一个using。确保您确实在XmlSerialize 中更改回FileMode.Create。您应该做的另一件事是确保在 kList(文件)不存在时创建它。
  • 感谢它现在可以工作了。你能解释一下 using 做了什么吗?
  • 它基本上确保你正在使用的东西已经被处理掉并且有更长的解释here但是为了使用'使用'类必须实现IDisposible
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2019-07-20
  • 1970-01-01
  • 2011-07-12
  • 1970-01-01
  • 1970-01-01
  • 2016-09-05
  • 2020-08-21
相关资源
最近更新 更多