数据访问层使用XML文件

本文关键字:XML 文件 访问 数据 | 更新日期: 2023-09-27 18:17:28

我想创建一个数据访问层,支持CRUD方法,并使用XML文件的底层存储。
我是XML的新手,我不太确定如何使用XmlDocument, XDocument, XmlSerializer等。
下面是我对数据访问类的基本想法:

public class EmployeesDao
    {
        private const string FILE_NAME = "file.xml";
            //an XDocument which contains all the employees records
        private XDocument m_XDocument;
        private XmlSerializer m_XmlSerializer;

        public TestCasesDao()
        {
            //is this correct?
                    m_XDocument = XDocument.Load(@"c:'" + FILE_NAME);
            m_XmlSerializer = new XmlSerializer(typeof(EmployeeDTO));
        }
        public void Save(IEmployee employee)
        {
            var dto = new EmployeeDTO(employee);
            //TODO: serialize the DTO, add it to the XDocument, and save to file
        }
        public IEmployee GetEmployee(string name)
        {
                    //TODO: retrieve an EmployeeDTO from my XDocument
                    return employeeDto.Convert();  //return an IEmployee
        }
            //TODO: update and delete methods...
    }

关于如何填补缺失的空白有什么想法吗?

数据访问层使用XML文件

这取决于你的需求是什么。在DAL中使用XML只对小型项目有意义,即使在这种情况下,SQLite也可能是更好的解决方案。XML的唯一"好处"是它是一种文本的、人类可读的格式,但从这个意义上说,它更适合作为导出文件,而不是实际的DAL技术。任何"手工制作"的单文件数据库系统的问题是,每次进行更改时,您都需要保存整个文件(如果您不选择内存映射文件,根据您的需要,这可能是多余的)。

对于每一个插入或更新操作,你都需要一个读取器和一个写入器,以便将所有的记录复制到一个新文件中。根据你的文件大小,一个选项可能是在你的应用程序生命周期内将记录保存在内存中,并每隔一段时间将它们刷新到磁盘。它将是一个静态可用的列表(考虑并发性),但只有在数据库相对较小时才有意义。

您最关心的可能是一致性和事务完整性。如果有两个进程同时使用同一个XML文件,则很难同步访问。此外,应用程序崩溃或电源故障可能会使您的数据损坏,这意味着您还应该考虑某种日志系统。例如,SQLite,乍一看似乎很简单,但它是ACID,并为此付出了大量的努力(如果您有时间,请查看这篇冗长的文章以获得一个概念)。从头开始实现这一点确实是多余的。

所以,总结一下,你的选择是:
  1. 你只有一个进程使用一个文件。

    。数据库很小:将它保存在内存中,锁定所有操作,并定期刷新它。相对简单。

    b。数据库太大:

    • 使用读写器组合在每次操作时复制整个文件。

    • 保持命令队列并批量刷新它们。更快,增加了一些事务支持,但比较复杂。

  2. 其他进程可以访问该文件

    。实现日志机制以防止同时访问。

    b。

在任何情况下,您可能需要保留一个事务性日志文件,并使用它来确保访问之间的数据是一致的。你的应用程序应该能够自己从失败中恢复。我的观点是,SQLite可能是一种可行的方法:结合像NHibernate这样的ORM解决方案,使用起来真的很简单和安全。

对于序列化,可以使用泛型方法

public static class GenericSerializer
{
    public static string Serialize<T>(ICollection<T> listToSerialize)
    {
        MemoryStream stream = new MemoryStream();
        XmlSerializer xmlSerializer;
        try
        {
            xmlSerializer = new XmlSerializer(typeof(List<T>));
            xmlSerializer.Serialize(stream, listToSerialize);
            return Encoding.UTF8.GetString(stream.ToArray());
        }
        finally
        {
            stream.Close();
        }
    }
    public static string Serialize<T>(T objectToSerialize)
    {
        MemoryStream stream = new MemoryStream();
        XmlSerializer xmlSerializer;
        try
        {
            xmlSerializer = new XmlSerializer(typeof(T));
            xmlSerializer.Serialize(stream, objectToSerialize);
            return Encoding.UTF8.GetString(stream.ToArray());
        }
        finally
        {
            stream.Close();
        }
    }
  public static T Deserialize<T>(string xmlDataToeSerialize)
    {
        XmlSerializer xmlDeSerializer = new XmlSerializer(typeof(T));
        StringReader stringReader = new StringReader(xmlDataToeSerialize);
        return (T)xmlDeSerializer.Deserialize(stringReader);            
    }
}

用于更新和删除您可以从文件中检索集合或对象并编辑和覆盖现有的集合或对象,或者您可以使用XPath表达式直接编辑XML

XML/0340 _XPath.htm"> http://www.java2s.com/Tutorial/CSharp/0540_ XML/0340 _XPath.htm