C# deserialization using reflection
I have a .dll that deserializes a class. When I call this .dll from a project or not using reflection it works fine. When I call the .dll using reflection I get an error on the line that deserializes. I know this is due isolation that happens when I use reflection to load an assembly. Wondering if anyone has any fix or an idea of how to implement this? BTW, the serialization works just fine, it's just the deserialization that doesnt work.
I tried both binary and xml, here's the code:
static public object SerializeLoad(string sFilename)
{
try
{
List<ElementTodo> _object = null;//ElementTodo _object = null;
Stream stream = File.Open(sFilename, FileMode.Open);
//BinaryFormatter bformatter = new BinaryFormatter();
XmlSerializer bformatter = new XmlSerializer(typeof(ElementTodo), "ToDo");
//_object = (_object.GetType())bformatter.Deserialize(stream);
_object = (List<ElementTodo>)bformatter.Deserialize(stream);
stream.Close();
return _object;
}
catch(Exception e)
{
string error = e.Message;
return null;
}
开发者_开发知识库 }
The generated XML is as follows:
<
?xml version="1.0"?>
<ArrayOfElementTodo xmlns:xsi="w3.org/2001/XMLSchema-instance"; xmlns:xsd="w3.org/2001/XMLSchema"; xmlns="ToDo">
<ElementTodo Title="a" content="aa" isDone="false" />
<ElementTodo Title="b" content="bb" isDone="false" />
<ElementTodo Title="c" content="cc" isDone="false" />
<ElementTodo Title="d" content="dd" isDone="false" />
</ArrayOfElementTodo>
I assume that ElementTodo is in an assembly that both your code and the assembly loaded using reflection have access to? What you have to be careful of is that your loaded assembly is using the same dependent assembly and doesn't load a new copy. Otherwise you wind up with fun errors like 'Object X (of type ElementTodo) is not of type ElementTodo', since two copies of the types are loaded. It's hard to say for sure that this is your issue without more information on the specific error, however.
If this is your problem, you can address it by forcing assemblies to resolve to the version that's already loaded using something like this:
In your startup code somewhere:
//This is required because we load assemblies at runtime
//If this is not used, there can be problems when Reflecting over Types
AppDomain.CurrentDomain.AssemblyResolve += CurrentDomain_AssemblyResolve;
Implementation:
private static Assembly CurrentDomain_AssemblyResolve(object sender, ResolveEventArgs args)
{
return AppDomain.CurrentDomain.GetAssemblies().
FirstOrDefault(assembly => assembly.FullName == args.Name);
}
精彩评论