DataRow的序列化问题
2024-07-21 02:23:02
供稿:网友
国内最大的酷站演示中心!
在.net里,datarow类型的对象是不支持序列化的,那么如果在一个需要序列化的对象中含有datarow类型的字段该怎么办呢?呵呵,幸好datatable是支持序列化的。因此,我们可以自定义序列化的行为,并在序列化和反序列化的时候用datatable来对datarow进行包装和解包。
为了自定义序列化行为,必须实现iserializable接口。实现这个接口要实现 getobjectdata 方法以及在反序列化对象时使用的特殊构造函数。前者的作用是把该对象要封装的数据加入到系统提供的一个容器中,然后系统会对这些数据进行序列化;后者的作用是把反序列化的数据从容器中取出来,然后显式的赋值给该对象的某一个字段。
如下例所示,应当注意的代码用黑体标出。
using system;
using system.data;
using system.runtime.serialization.formatters.binary;
using system.runtime.serialization;
using system.io;
using system.security.permissions;
namespace phenix.dl
{
/// <summary>
/// field 的摘要说明。
/// </summary>
[serializable]
public class field:iserializable
{
private string name="";
private datarow dr=null;
private string title="";
private int index=-1;
public int index
{
get{return this.index;}
set{this.index=value;}
}
public string title
{
get{return this.title;}
set{this.title=value;}
}
public string fieldname
{
get{return this.name;}
set{this.name=value;}
}
public datarow fieldinfo
{
get{return this.dr;}
set{this.dr=value;}
}
public field()
{
//
// todo: 在此处添加构造函数逻辑
//
}
protected field(serializationinfo info, streamingcontext context)//特殊的构造函数,反序列化时自动调用
{
this.name=info.getstring("fieldname");
this.title=info.getstring("fieldtitle");
this.index=info.getint32("fieldindex");
datatable dt=info.getvalue("fieldinfo",new datatable().gettype()) as datatable;
this.dr=dt.rows[0];
}
[securitypermissionattribute(securityaction.demand,serializationformatter=true)]
public virtual void getobjectdata(serializationinfo info, streamingcontext context)//序列化时自动调用
{
info.addvalue("fieldname", this.name);
info.addvalue("fieldtitle", this.title);
info.addvalue("fieldindex", this.index);
datatable dt=this.dr.table.clone(); //datarow不能同时加入到两个datatable中,必须先克隆一个
datarow row=dt.newrow();
row.itemarray=dr.itemarray;
dt.rows.add(row);
info.addvalue("fieldinfo",dt,dt.gettype());
}
public override string tostring()
{
return this.name;
}
}
}