MicroHelper.Net

雷锋说.对待朋友要MicroHelper,对待敌人要害尔扑
随笔 - 74, 评论 - 431, 引用 - 7

导航

工具

关于

邮件系统不稳定,使用songdming at 263 dot net吧
PageRank

FastCounter by bCentral

 

标签

每月存档

广告



访客

 

A:DataReader 直接绑定,B: DataReader直接转换成EntityCollection,C:用Reflection将DataReader转换成EntityCollection,三种方式到底速度差多少?

用2000笔数据作试验。测试下来,直接转换成EntityCollection所化的时间与直接绑定相差无几,大概是1~1.5倍,用Reflection将DataReader转换成EntityCollection所化时间是直接绑定的4~5倍左右,用注释起来的代码的话花的时间就多了,大概8倍的样子。

但是转化成EntityCollection,还要写代码来处理排序。

直接绑定大致如此

  private void BindByDirect(SqlDataReader dr)
  {
   contactData.DataSource= dr;
   contactData.DataBind();
  }

用EntityCollection

  private void BindByEntityCollection(SqlDataReader dr)
  {
   ContactCollection contacts = new ContactCollection();
   while(dr.Read())
   {
    Contact contact = new Contact();
    contact.Contact_ID = dr["Contact_ID"].ToString();
    contact.Contact_LastName = dr["Contact_LastName"].ToString() ;
    contact.Contact_JobTitle = dr["Contact_JobTitle"].ToString();
    contact.Contact_Department = dr["Contact_Department"].ToString();
    contact.Contact_Rank = dr["Contact_Rank"].ToString();
    contacts.Add(contact);
   }
   contactData.DataSource= contacts;
   contactData.DataBind();
  }

借助反射

private void BindByReflection(SqlDataReader dr)
  {
   ContactCollection contacts = new ContactCollection();
   Type objType = typeof(Contact);
   PropertyInfo[] properties = objType.GetProperties(BindingFlags.Public | BindingFlags.Instance);
   Type fieldAttributeType  = typeof(FieldAttribute);

   while(dr.Read())
   {
    //Contact contact = new Contact();
    //foreach (PropertyInfo property in properties)
    //{
    // FieldAttribute fieldAttribute = (FieldAttribute) Attribute.GetCustomAttribute(
    //  property, fieldAttributeType);

    // property.SetValue(contact,dr[fieldAttribute.ColumnName].ToString(),null);
    //}

    object instance = Activator.CreateInstance(objType, true);
    for (int i=0; i < properties.Length; i++)
    {
     FieldAttribute[] fieldAttributes = (FieldAttribute[])properties[i].GetCustomAttributes(fieldAttributeType, true);
     if (fieldAttributes.Length > 0)
     {
      properties[i].SetValue(instance, dr[fieldAttributes[0].ColumnName].ToString(), null);
     }
    }
    contacts.Add(instance );
   }
   contactData.DataSource= contacts;
   contactData.DataBind();
  }
 }

public class  Contact
{
  string contact_ID;
  [FieldAttribute("Contact_ID")]
  public string Contact_ID
  {
   get {return contact_ID;}
   set {contact_ID = value;}
  }
}

相关文章

打印 | 张贴于 2004-04-21 20:48:00 | Tag:Dot Net

留言反馈

#回复: 让数据来证明 编辑
to @kuber
多谢
用缓存速度提高了30-40%,原理很简单,当时咋就没想到测试这种方案呢:)
2004-04-22 10:56:00 | [匿名用户:microhelper]
#回复: 让数据来证明 编辑
呵呵,同变,同变
我的方案是可以指定映射,也可以指定Table,这样就到数据库里面取Schema, 用FieldName和ColumnName相等来映射; 比较适合l懒人,呵呵;
2004-04-22 10:49:00 | [匿名用户:kuber]
#回复: 让数据来证明 编辑
有用xml做映射的
也有用customer attribute的
但估计没人像我这样BT的
我是直接用SQL从数据库中取结构信息的
当然结构信息都做了缓存处理
2004-04-22 10:42:00 | [匿名用户:progame]
#回复: 让数据来证明 编辑
我的环境是P4 1.5G+512M, Win2K SP4, VS2003在 Debug下运行
2004-04-22 10:32:00 | [匿名用户:kuber]
#回复: 让数据来证明 编辑
我只测了把数据从DataReader读到Collection,没有绑定. 2001条数据是100ms; 不实现ICloneable的话是150ms; 对Column的映射没有用CustomAttributes. 是在XML配置文件中作的. 我的观点跟progame 一样,Persist实现最好不要跟Entity放在一起;
考虑到重用性, 我觉得这样的性能开销是可以接受的

数据结构:
public class DTOUser : ICloneable
{
public DTOUser() {}
public DTOUser(int Id, string Name, int Type, string Desc, DateTime CreateTime, byte[] Version)
{
this.Id = Id;
this.Name = Name;
this.Type = Type;
this.Desc = Desc;
this.CreateTime = CreateTime;
this.Version = Version;
}

public int Id;
public string Name;
public int Type;
public string Desc;
public System.DateTime CreateTime;
public byte[] Version=null;

public object Clone()
{
return this.MemberwiseClone();
}
}
2004-04-22 10:28:00 | [匿名用户:kuber]
#回复: 让数据来证明 编辑
1、我电脑是p3 833的
2、我测试的表结构是这样的
CREATE TABLE [dbo].[TDalop] (
[autoid] [int] IDENTITY (1, 1) NOT NULL ,
[uid] [varchar] (12) NOT NULL ,
[code] [varchar] (50) NOT NULL ,
[name] [varchar] (50) NOT NULL ,
[salary] [numeric](18, 0) NOT NULL ,
[indate] [datetime] NULL ,
[remark] [varchar] (50) NULL ,
[ismanager] [bit] NOT NULL ,
[rowversion] [timestamp] NOT NULL,
[guid] [uniqueidentifier] NULL,
[photo] [image] NULL
) ON [PRIMARY]
GO
2004-04-22 10:01:00 | [匿名用户:progame]
#回复: 让数据来证明 编辑
我是用反射,但可以把Type的properties和FieldAttribute缓存起来,这样效率高很多. 构造实例的时候可以检查是否是IClonable,是的话,用缓存的实例Clone一个.
2004-04-22 09:58:00 | [匿名用户:kuber]
#回复: 让数据来证明 编辑
上面2000笔数据处理,直接绑定大概70毫秒左右
2004-04-22 09:50:00 | [匿名用户:microhelper]
#回复: 让数据来证明 编辑
上面漏了一句
do while not list.eof
set contact = list.current(contact)
debug.print contact.name
list.movenext
loop
2004-04-21 22:32:00 | [匿名用户:progame]
#回复: 让数据来证明 编辑
我也用数据来说话(我的dalop):

一种是EntityList(对RecordSet的包装),然后遍历(通过callbyname赋值),1000条数据,0.6s
一种是EntityCollection,将EntityList中的数据填充到Collection中(new 再 callbyname),同样数据,大概是2s多

所以我认为EntityList是对EntityCollection的一种很好的补充。

EntityList使用方法
dim contact as new contact
dim list as entitylist

....
do while not list.eof
set contact = list.current(contact)
debug.print contact.name
loop
2004-04-21 22:31:00 | [匿名用户:progame]
对不起,目前本随笔不允许发表新评论.

Powered by: Joycode MVC Blogger System