解决反序列化(Deserialize)无法找到程序集的错误
Posted
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了解决反序列化(Deserialize)无法找到程序集的错误相关的知识,希望对你有一定的参考价值。
http://blog.csdn.net/w_s_q/article/details/5677536
在使用.NET序列化对象时,会将程序集信息也包含进去。如果将序列化之后的字节数组通过网络(或其他传输方式)传输到另一个应用程序,再使用Deserialize反序列化还原对象时,可能(注意是可能)会出现无法找到程序集的错误。之所以说是可能,是因为如果两边的应用程序结构(命名空间、类结构、程序名、程序签名、程序版本等)相同,则不会出现该错误。下面说一个具体实例:
在客户端动态生成一条SELECT语句,将该语句发送到服务器执行,再将执行后的结果返回给客户端。(题外话:要实现本功能完全可以不使用序列化和反序列化的方法,本实例只是为了解释如何解决反序列化时出现的无法找到程序集的错误)
解决方案:
创建一个.NET类库,把要传输的对象做成一个结构或类放在类库(假设为ClassLib.dll)中。如:
view plaincopy to clipboardprint?
[Serializable]
public struct Data
{
public string sql;
}
[Serializable]
public struct Data
{
public string sql;
}
然后在客户端程序(假设为Client.exe)中引用ClassLib.dll,创建Data对象,给Data.sql赋值,再调用Serialize方法将Data对象序列化成字节数组发送出去。参考代码:
view plaincopy to clipboardprint?
BinaryFormatter formatter = new BinaryFormatter();
MemoryStream mem = new MemoryStream();
ClassLib.Data data;
data.sql="select * from table";
formatter.Serialize(mem, data);
mem.Seek(0, SeekOrigin.Begin);
byte[] buffer = mem.GetBuffer(); //这里使用mem.GetBuffer()要比mem.ToArray()效率高,
//因为前者直接返回mem使用的内存,后者是创建一块合适大小的内存,
//再将mem对象缓存中的数据拷贝进去。
//但是如果改变使用GetBuffer方法返回的数组中数据的值,
//则mem对象缓存中的值也会变化
Send(buffer, mem.Length); //Send原型为 void Send(byte[] buf, long bufLen)
//之所以Send函数要有第2个参数bufLen,
//是因为使用GetBuffer方法返回的缓存中有未使用的字节
//通过给该参数传递mem.Length可以让Send函数只发送使用的字节
BinaryFormatter formatter = new BinaryFormatter();
MemoryStream mem = new MemoryStream();
ClassLib.Data data;
data.sql="select * from table";
formatter.Serialize(mem, data);
mem.Seek(0, SeekOrigin.Begin);
byte[] buffer = mem.GetBuffer(); //这里使用mem.GetBuffer()要比mem.ToArray()效率高,
//因为前者直接返回mem使用的内存,后者是创建一块合适大小的内存,
//再将mem对象缓存中的数据拷贝进去。
//但是如果改变使用GetBuffer方法返回的数组中数据的值,
//则mem对象缓存中的值也会变化
Send(buffer, mem.Length); //Send原型为 void Send(byte[] buf, long bufLen)
//之所以Send函数要有第2个参数bufLen,
//是因为使用GetBuffer方法返回的缓存中有未使用的字节
//通过给该参数传递mem.Length可以让Send函数只发送使用的字节
在服务器端(假设为Server.exe)中也引用ClassLib.dll,调用Deserialize函数反序列化接收到的字节得到Data对象。参考代码:
view plaincopy to clipboardprint?
ClassLib.Data data = (ClassLib.Data)formatter.Deserialize(new MemoryStream(data, index, length));
ClassLib.Data data = (ClassLib.Data)formatter.Deserialize(new MemoryStream(data, index, length));
至此序列化和反序列化完成。今后在库变换时,只要保证服务器和客户端的库一致,就可以了。
以上是关于解决反序列化(Deserialize)无法找到程序集的错误的主要内容,如果未能解决你的问题,请参考以下文章
C#序列化与反序列化(Serialize,Deserialize)实例详解
Newtonsoft.Json反序列化(Deserialize)报错问题
JSON.Net无法在自定义JsonConverter中反序列化json数组
SpringBoot 集成MyBatis-Plus提示反序列化异常:cannot deserialize from Object value (no delegate- or property-bas
post请求 参数json序列化报错: cannot deserialize from Object value
[leetcode]297. Serialize and Deserialize Binary Tree 序列化与反序列化二叉树