从 DataTable 读取/比较行信息时,哪个通常最快?
'assume dt as datatable'
'method 1'
dim i as int32
for i = 0 to dt.rows.count - 1
....
next
'method 2'
dim row as datarow
for each row in dt.rows
....
next
如果有区别,在什么情况下使用其中一种是值得的?
提前感谢您的任何指导!
从 DataTable 读取/比较行信息时,哪个通常最快?
'assume dt as datatable'
'method 1'
dim i as int32
for i = 0 to dt.rows.count - 1
....
next
'method 2'
dim row as datarow
for each row in dt.rows
....
next
如果有区别,在什么情况下使用其中一种是值得的?
提前感谢您的任何指导!
编译器将 For Each 扩展为一个短暂的 while 循环。
for each row in dt.rows
// expands to:
IEnumerator e = dt.rows.GetEnumerator()
while e.MoveNext()
row = e.Current
因此,您需要支付少量的间接费用。但是为了清楚起见,如果您只处理一行并且没有修改数据集,我仍然会坚持使用 For Each。
实际上没有区别。尽管从技术上讲,通过 IEnumerable 接口,您在 foreach 方法中付出了很小的代价。
第二个将受到轻微处罚。但是,就情况而言,为了代码的清晰,我总是会使用方法 2。但是,如果我需要在分析当前行时访问下一行/上一行等操作,我会使用方法 1。
好吧,这是有区别的,因为在 foreach 循环中调用的 GetEnumerator 和 MoveNext 是虚拟的(调用需要通过指针),因此不能内联。这个开销实际上很小,除非你做很多循环。
在某些情况下,尽管编译器会将 foreach 替换为 for 循环(我相信在迭代数组时)。
为了清晰起见,我个人更喜欢在我的 ASP.NET MVC 代码中使用 foreach,正如许多人在这里所说的那样,但也经常使用 for 循环。Joe Duffy 最近发表了一篇关于枚举成本的有趣文章 http://joeduffyblog.com/2008/09/21/the-cost-of-enumerating-in-net/
@gdean232 是对的 - 几乎没有区别。如果性能是一个问题,使用 SqlDataReader 会明显更快。
foreach 的实现实际上比标准的实现要快一些,因为每个索引数组的访问都需要进行边界检查。但是,由于成语:
for(int i =0; i < myArray.Count; ++i)
{
// do something with myArray[i];
}
很常见,编译器会寻找它作为特例并对其进行优化,因此它变得更快。但是,任何与该格式的微小偏差(例如 int len = MyArray.Count; for(int i =0; i< len; ++i))都不会被识别,并且会使用较慢的代码。