DataTable处理大数据量时的效率问题

tianyi724 2008-07-10 09:03:23
现在有两个个DataTable,分别为tbA,tbB
tbA中有六万条数据,tbB中数据忽略不计。
其中,tbA中定义了主键 tbA.PrimaryKey={tbA.a,tbA.b}

对tbA执行循环操作,从第一条数据开始,直到最后一条数据

For i=0 To DataTableA.Rows.Count
drCurrent=dtB.Rows.Find(tbA.Rows(i).a,tbA.Rows(i).b) '该数据在tbB中是否存在
IF drCurrent=NULL '该数据不存在的情况下,向tbB中追加一条记录
dtB.Rows.Add(...)
dtB.AcceptChanges()
END IF
NEXT

以一万次循环为单位,通过对时间的计算,发现随着tbB中的数据越来越多,循环一万次花的时间比前一次一成倍的速度在增长。
问题是:
1.有没有什么好的方法,可以调高效率。
2.当我把dtB.AcceptChanges提到循环外面时,效率明显得到提高。但是,在循环体内,需要用到更改后了的dtB。这样做的话会影响到程序的正确性么。

谢谢。
...全文
1460 13 打赏 收藏 转发到动态 举报
写回复
用AI写文章
13 条回复
切换为时间正序
请发表友善的回复…
发表回复
ziyan688999 2010-05-04
  • 打赏
  • 举报
回复
是的。速度可能会慢
tangweikai 2008-07-11
  • 打赏
  • 举报
回复
有遇到过相同问题,后来使用了此方案:
1. 建立第3个表来存放新增的行 dim gg as datatable= tbB.clone

2.新增时,将记录增到 GG 表中,待Find()完成后,再将 GG 新增到tbB表中..

这样效率会高很多..
crossrowman 2008-07-11
  • 打赏
  • 举报
回复

应该从两个表的结构上去下手:

drCurrent=dtB.Rows.Find(tbA.Rows(i).a,tbA.Rows(i).b) '这个语句将被执行 6w次 循环每执行一次 就可能增加这个语句的成本 这是完全没有必要的


看看下面的代码效率是否能高一些?


DataRow[] ARows = DataTableA.Select ("", "a,b" );//将DataTableA中的数据进行排序
//这个排序占用的时间是这段代码中最多的, 如果 TableA已经有某一个顺序了,则不用排A的序,将B也按照这个顺序排,可以节省不少时间


DataRow[] BRows = DataTableB.Select ("", "a,b" );//将DataTableB中的数据进行排序 注意两个排序都是按照主键的同一顺序进行的

int IndexB = 0;

for(int i =0;i<ARows.Length;i++)
{
if(IndexB >= BRows.Length || ARows[i][a]!= BRows[IndexB][a] || ARows[i][b]!= BRows[IndexB][b])
{
dtB.Rows.Add(...) ; //追加记录
//.....
}
else
{
IndexB ++;
}
}
mainbaby 2008-07-11
  • 打赏
  • 举报
回复
我觉得你可以循环B表,把A表里有相同数据的删掉,然后再把A表里剩余的数据一次性加到B表里
tianyi724 2008-07-11
  • 打赏
  • 举报
回复
结贴!!

谢谢大家的回答。
经过艰苦的测试,我发现最耗时间的并不是 dtB.Rows.Find(tbA.Rows(i).a,tbA.Rows(i).b)
相反,Rows.Find的效率是很高的,因为当dtB中有一万条数据 和 有 六万条数据时执行这句话所花的时间是基本是一样的。
最耗时间的语句是 dtB.AcceptChanges() 。这句话是多余的。经过对运行后数据的比较,没有这句话完全不影响程序的正确性。

谢谢crossrowman和tangweikai 的方案,相信以后会用的着。
HimeTale 2008-07-10
  • 打赏
  • 举报
回复
[Quote=引用 7 楼 tianyi724 的回复:]
引用 1 楼 HimeTale 的回复:
dtB.AcceptChanges() 这句删掉效率就高了


删掉的话,的确可以非常明显的提高效率。但是,这样做安全么?
AcceptChanges在这里究竟是起什么作用的阿,是否是多余的?
[/Quote]
绝对多余
除非你需要用到RowState或者RejectChanges
tianyi724 2008-07-10
  • 打赏
  • 举报
回复
[Quote=引用 1 楼 HimeTale 的回复:]
dtB.AcceptChanges() 这句删掉效率就高了
[/Quote]

删掉的话,的确可以非常明显的提高效率。但是,这样做安全么?
AcceptChanges在这里究竟是起什么作用的阿,是否是多余的?
三下鱼 2008-07-10
  • 打赏
  • 举报
回复
[Quote=引用 4 楼 seesea125 的回复:]
datatable是放内存中的,如果数据量大,效率会急速下降,你可以测试一下就知道了
[/Quote]
LiloZhu 2008-07-10
  • 打赏
  • 举报
回复
你可以先循环查询tbA 中的数据在table 中是否存在,如果存在就删除tbA中的此条记录,对tabA做完查询检测后,在一次性将tbA表的剩下数据都 Insert 到 tbB
seesea125 2008-07-10
  • 打赏
  • 举报
回复
datatable是放内存中的,如果数据量大,效率会急速下降,你可以测试一下就知道了
wuyanteng1 2008-07-10
  • 打赏
  • 举报
回复
不要每次都从头开始循环不就结了吗
Jinglecat 2008-07-10
  • 打赏
  • 举报
回复
tbA中定义了主键 tbA.PrimaryKey={tbA.a,tbA.b}

dtB.Rows.Find(tbA.Rows(i).a,tbA.Rows(i).b) '该数据在tbB中是否存在

=========

在 dtB 中搜索,应该在 dtB 定义主键以便索引
HimeTale 2008-07-10
  • 打赏
  • 举报
回复
dtB.AcceptChanges() 这句删掉效率就高了

16,717

社区成员

发帖
与我相关
我的任务
社区描述
VB技术相关讨论,主要为经典vb,即VB6.0
社区管理员
  • VB.NET
  • 水哥阿乐
  • 无·法
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
暂无公告

试试用AI创作助手写篇文章吧