.NET,C#:如何添加充当ISerializable接口的自定义序列化属性

我正在做一些db linq对象的序列化,它包含EntitySet和EntityRef类。

我找到了一种非常简单的方法来处理这些类的序列化,只需使用ISerializable来正确处理这种类型的成员(将它们转换为序列化列表,并在反序列化时撤消它)。

但是,如果我能这样做,那将是非常好的:

[Serializable] [SerializeLinqEntities] partial class Person { ... } 

代替:

 partial class Person : ISerializable { public virtual void GetObjectData( SerializationInfo si, StreamingContext ctxt ) { EntitySerializer.Serialize(this, typeof(Person), si, ctxt); } protected Person( SerializationInfo si, StreamingContext ctxt ) { EntitySerializer.Deerialize(this, typeof(Person), si, ctxt); } } 

有没有办法做到这一点? 我查看了序列化类,似乎无法找到任何方法来设置自定义序列化filter例程(我可以在那里查找我的自定义属性)。

谢谢!

是的,您可以通过实现ISerializationSurrogate和ISurrogateSelector接口来实现此目的 。

像这样的东西:

 [AttributeUsage(AttributeTargets.Class)] public class SerializeLinqEntities : Attribute { } public class LinqEntitiesSurrogate : ISerializationSurrogate { public void GetObjectData( object obj, SerializationInfo info, StreamingContext context) { EntitySerializer.Serialize(this, obj.GetType(), info, context); } public object SetObjectData( object obj, SerializationInfo info, StreamingContext context, ISurrogateSelector selector) { EntitySerializer.Deerialize(obj, obj.GetType(), info, context); return obj; } } ///  /// Returns LinqEntitySurrogate for all types marked SerializeLinqEntities ///  public class NonSerializableSurrogateSelector : ISurrogateSelector { public void ChainSelector(ISurrogateSelector selector) { throw new NotImplementedException(); } public ISurrogateSelector GetNextSelector() { throw new NotImplementedException(); } public ISerializationSurrogate GetSurrogate( Type type, StreamingContext context, out ISurrogateSelector selector) { if (!type.IsDefined(typeof(SerializeLinqEntities), false)) { //type not marked SerializeLinqEntities selector = null; return null; } selector = this; return new LinqEntitiesSurrogate(); } } [SerializeLinqEntities] public class TestSurrogate { public int Id { get; set; } public string Name { get; set; } } class Program { static void Main(string[] str) { var ns1 = new TestSurrogate {Id = 47, Name = "TestName"}; var formatter = new BinaryFormatter(); formatter.SurrogateSelector = new NonSerializableSurrogateSelector(); using (var ms = new MemoryStream()) { formatter.Serialize(ms, ns1); ms.Position = 0; var ns2 = (TestSurrogate) formatter.Deserialize(ms); // Check serialization Debug.Assert(ns1.Id == ns2.Id); Debug.Assert(ns1.Name == ns2.Name); } } } 

遗憾的是, ISerializable是一个设计用于控制序列化过程的接口,而SerializableAttribute只是一个标记,表示“此类可以序列化”。 但是,您可以查看类似PostSharp的内容来添加此function(请查看CompositionAspect )。