开发者

.NET binary serialization conditionally without ISerializable

开发者 https://www.devze.com 2023-02-02 19:18 出处:网络
I got 2 classes, for example: public class A { private B b; ... } public class B { ... } I need to serialize an object A using BinaryFormatter. When remoting it shall include the field b, but not

I got 2 classes, for example:

public class A
{
    private B b;
    ...
}

public class B
{
    ...
}

I need to serialize an object A using BinaryFormatter. When remoting it shall include the field b, but not when serialize to file. Here is what I added:

[Serializable]
public class A : MarshalByRefObject
{
        private B b;

        [OnSerializing]
        private void OnSerializing(StreamingContext context)
        {
            if (context.State == StreamingContextStates.File)
            {
                this.b = null;        
            }
        }
    ...
}

[Serializable]
public class B : MarshalByRefObject
{
    ...
}

I think this is a bad design because if another class C also contains B, in class C we must add the duplicate OnSerializing() logic as in A. Class B should decide what to do, not class A or C.

I don't want to use ISerializable interface because there are too many variable开发者_开发问答s in class B have to be added to SerializationInfo.

I can create a SerializationSurrogate for class B, which perform nothing in GetObjectData() & SetObjectData(), then use it when serializing to file. However the same maintenance issue because whoever modify class B can't notice what going to happen during serialization & the existence of SerializationSurrogate.

Is there a better alternative?


The real problem is here is using Serializable (iow trying to serialize) a MarshalByRefObject derived type which is pretty much impossible if the object lives in another domain.

Use one or the other, but not both.


Ok, I have misconception of MarshalByRefObject. It doesn't serialize thus I can use [NonSerializable] for file serialization.

Nevertheless, I do have some classes that marked with [Serializable] in order to marshal by value when remoting. Therefore need to differentiate it from file serialization:

[Serializable]  
public class A 
{          
    private B b;      

    [OnSerializing]          
    private void OnSerializing(StreamingContext context)          
    {              
        if (context.State == StreamingContextStates.File)              
        {                  
            this.b = null;                      
        }          
    }      
    ...  
}    

[Serializable]  
public class B 
{      
    ...
 }

[NonSerialized] doesn't help in this case because:
1) Need to serialize field b when remoting but not to disk.
2) If class C, D, E, etc also have field b, have to update all of them with [NonSerialized]. Too many maintenance tasks.

Is there a better alternative?

0

精彩评论

暂无评论...
验证码 换一张
取 消

关注公众号