C# 什么';在没有序列化属性的情况下,将对象保存到文件的最简单方法是什么?

C# 什么';在没有序列化属性的情况下,将对象保存到文件的最简单方法是什么?,c#,xml,serialization,C#,Xml,Serialization,我在c#中有不同类型的对象,我希望将其保存到文件中(首选XML),但我不能使用序列化,因为该类不是由我编写的,而是来自DLL 最好的解决方案是什么?围绕DLL的不可序列化类编写您自己的可序列化包装 编辑:评论中建议使用AutoMapper,我还没有听说过,但现在我听说了,我肯定会使用它,而不是自己编写包装。除非捕获不可序列化对象的某些内部状态需要一些反射(如果可能的话),否则我不知道AutoMapper是否提供了任何东西,或者您必须看看是否可以在包装器中捕获它。我将编写一个POCO(普通的旧类对

我在c#中有不同类型的对象,我希望将其保存到文件中(首选XML),但我不能使用序列化,因为该类不是由我编写的,而是来自DLL


最好的解决方案是什么?

围绕DLL的不可序列化类编写您自己的可序列化包装

编辑:评论中建议使用AutoMapper,我还没有听说过,但现在我听说了,我肯定会使用它,而不是自己编写包装。除非捕获不可序列化对象的某些内部状态需要一些反射(如果可能的话),否则我不知道AutoMapper是否提供了任何东西,或者您必须看看是否可以在包装器中捕获它。

我将编写一个POCO(普通的旧类对象)类,模拟返回的DLL中的对象。通常,如果您正在使用,.NET3.5或更高版本,我相信您有能力使用LINQ。我喜欢Linq将对象放入其他类中,或者对它们执行排序或其他操作

下面是一个简单的示例,例如,在返回对象中使用dummy。请记住,在DLL中,您当然可以有许多不同的对象,并且可以多次执行此操作。我也会将我的方法封装在它们自己的类中,以实现可重用性,而不是在主类中进行。但这里有一个简单的概念证明

using System;
using System.Linq;
using System.Windows.Forms;
using System.IO;
using System.Xml.Serialization;
using System.Collections.Generic;
using System.Xml.Linq;

namespace ExampleSerializer
{
    class Program
    {
        // example class to serialize
        [Serializable]
        public class SQLBit
        {
            [XmlElement("Name")]
            public string Name { get; set; }

            [XmlText]
            public string data { get; set; }
        }

        // example class to populate to get test data
        public class example
        {
            public string Name { get; set; }
            public string data { get; set; }
        }

        static void Main(string[] args)
        {
            string s = "";

            // make a generic and put some data in it from the test
            var ls = new List<example> { new example { Name = "thing", data = "data" }, new example { Name = "thing2", data = "data2" } };

            // make a second generic and put data from the first one in using a lambda
            // statement creation method.  If your object returned from DLL is a of a
            // type that implements IEnumerable it should be able to be used.
            var otherlist = ls.Select(n => new SQLBit
                {
                    Name = n.Name,
                    data = n.data
                });

            // start a new xml serialization with a type.
            XmlSerializer xmler = new XmlSerializer(typeof(List<SQLBit>));

            // I use a textwriter to start a new instance of a stream writer
            TextWriter twrtr = new StreamWriter(@"C:\Test\Filename.xml");

            // Serialize the stream to the location with the list
            xmler.Serialize(twrtr, otherlist);

            // Close
            twrtr.Close();

            // TODO: You may want to put this in a try catch wrapper and make up your 
            // own classes.  This is a simple example.
         }
    }
}
使用系统;
使用System.Linq;
使用System.Windows.Forms;
使用System.IO;
使用System.Xml.Serialization;
使用System.Collections.Generic;
使用System.Xml.Linq;
命名空间示例序列化程序
{
班级计划
{
//要序列化的示例类
[可序列化]
公共类SQLBit
{
[XmlElement(“名称”)]
公共字符串名称{get;set;}
[XmlText]
公共字符串数据{get;set;}
}
//要填充以获取测试数据的示例类
公开课范例
{
公共字符串名称{get;set;}
公共字符串数据{get;set;}
}
静态void Main(字符串[]参数)
{
字符串s=“”;
//制作一个泛型并将测试中的一些数据放入其中
var ls=new List{new example{Name=“thing”,data=“data”},new example{Name=“thing2”,data=“data2”};
//创建第二个泛型,并使用lambda将第一个泛型中的数据放入
//语句创建方法。如果从DLL返回的对象是
//实现IEnumerable的类型,它应该能够被使用。
var otherlist=ls.Select(n=>newsqlbit
{
名称,
数据
});
//使用类型启动新的xml序列化。
XmlSerializer xmler=新的XmlSerializer(typeof(List));
//我使用textwriter启动流编写器的新实例
TextWriter twrtr=新的StreamWriter(@“C:\Test\Filename.xml”);
//将流序列化到具有列表的位置
Serialize(twrtr,otherlist);
//接近
twrtr.Close();
//TODO:你可能想把它放在一个try-catch包装器中,然后组成你的
//这是一个简单的例子。
}
}
}
我认为问题标题中的“无序列化”一词具有误导性

如果我理解正确,您希望序列化没有序列化属性的对象


有像和这样的库可以为您完成这项工作。

我已经设计了一个快速的小扩展方法,在给定一个不可序列化的对象的情况下,它将“序列化”为XML。它相当粗糙,不需要进行大量检查,而且它生成的XML可以轻松调整以满足您的需要:

public static string SerializeObject<T>(this T source, bool serializeNonPublic = false)
{
    if (source == null)
    {
        return null;
    }

    var bindingFlags = BindingFlags.Instance | BindingFlags.Public;

    if (serializeNonPublic)
    {
        bindingFlags |= BindingFlags.NonPublic;
    }

    var properties = typeof(T).GetProperties(bindingFlags).Where(property => property.CanRead).ToList();
    var sb = new StringBuilder();

    using (var writer = XmlWriter.Create(sb))
    {
        writer.WriteStartElement(typeof(T).Name);
        if (properties.Any())
        {
            foreach (var property in properties)
            {
                var value = property.GetValue(source, null);

                writer.WriteStartElement(property.Name);
                writer.WriteAttributeString("Type", property.PropertyType.Name);
                writer.WriteAttributeString("Value", value.ToString());
                writer.WriteEndElement();
            }
        }
        else if (typeof(T).IsValueType)
        {
            writer.WriteValue(source.ToString());
        }

        writer.WriteEndElement();
    }

    return sb.ToString();
}
以及编号
3
对象
。生成的XML如下所示:

<?xml version="1.0" encoding="utf-16"?>
<Test>
  <Name Type="String" Value="John Doe" />
  <Age Type="Int32" Value="35" />
</Test>

<?xml version="1.0" encoding="utf-16"?>
<Int32>3</Int32>

<?xml version="1.0" encoding="utf-16"?>
<Object />

3.

分别。

我最终使用了JavaScriptSerializer,它正是我想要的:

List<Person> persons = new List<Person>();
persons.Add(new Person(){Name = "aaa"});
persons.Add(new Person() { Name = "bbb" });

JavaScriptSerializer javaScriptSerializer  = new JavaScriptSerializer();
var strData = javaScriptSerializer.Serialize(persons);

var persons2 = javaScriptSerializer.Deserialize<List<Person>>(strData);
List persons=新列表();
添加(newperson(){Name=“aaa”});
添加(newperson(){Name=“bbb”});
JavaScriptSerializer JavaScriptSerializer=新的JavaScriptSerializer();
var strData=javaScriptSerializer.Serialize(个人);
var persons2=javaScriptSerializer.Deserialize(strData);

你可以利用一个库,比如从一个可序列化对象复制到一个可序列化对象,然后保存/加载该对象。如果你在执行此操作后试图重建一个对象,请非常小心。。。对象可能存在某种未公开的内部状态,因此无法保存。序列化需要了解对象的实现。如果没有这一点,这可能非常困难。相反,我会看看是否可以重现创建对象所采取的操作。根据定义,将对象保存到文件就是序列化。
List<Person> persons = new List<Person>();
persons.Add(new Person(){Name = "aaa"});
persons.Add(new Person() { Name = "bbb" });

JavaScriptSerializer javaScriptSerializer  = new JavaScriptSerializer();
var strData = javaScriptSerializer.Serialize(persons);

var persons2 = javaScriptSerializer.Deserialize<List<Person>>(strData);