[转载]c#使用foreach需要知道的

[转载]c#使用foreach需要知道的 – smark – 博客园.

C#中通过foreach遍历一个列表是经常拿用的方法,使用起来也方便,性能上也和for没有多大的差别;那为什么还要注意呢?我们先下来看下以下这句话:分 配的内存数量和完成测试所需的时间之间有直接关系。当我们单独查看的时候,内存分配并不是非常昂贵。但是,当内存系统只是偶尔清理不使用的内存时,问题就 出现了,并且问题出现的频率和要分配的内存数量成正比。因此,你分配越多的内存,对内存进行垃圾回收的频率就越频繁,你的代码性能就会变得越差。

从上面那些话可以看到内存的回收是非常损耗资源,那我们再看下一些.net内部类型的实现。

Array:

<span class="com">// System.Array</span><span class="pln">
</span><span class="kwd">public</span><span class="pln"> </span><span class="typ">IEnumerator</span><span class="pln"> </span><span class="typ">GetEnumerator</span><span class="pun">()</span><span class="pln">
</span><span class="pun">{</span><span class="pln">
</span><span class="kwd">int</span><span class="pln"> lowerBound </span><span class="pun">=</span><span class="pln"> </span><span class="kwd">this</span><span class="pun">.</span><span class="typ">GetLowerBound</span><span class="pun">(</span><span class="lit">0</span><span class="pun">);</span><span class="pln">
</span><span class="kwd">if</span><span class="pln"> </span><span class="pun">(</span><span class="kwd">this</span><span class="pun">.</span><span class="typ">Rank</span><span class="pln"> </span><span class="pun">==</span><span class="pln"> </span><span class="lit">1</span><span class="pln"> </span><span class="pun">&</span><span class="pln">amp</span><span class="pun">;&</span><span class="pln">amp</span><span class="pun">;</span><span class="pln"> lowerBound </span><span class="pun">==</span><span class="pln"> </span><span class="lit">0</span><span class="pun">)</span><span class="pln">
</span><span class="pun">{</span><span class="pln">
</span><span class="kwd">return</span><span class="pln"> </span><span class="kwd">new</span><span class="pln"> </span><span class="typ">Array</span><span class="pun">.</span><span class="typ">SZArrayEnumerator</span><span class="pun">(</span><span class="kwd">this</span><span class="pun">);</span><span class="pln">
</span><span class="pun">}</span><span class="pln">
</span><span class="kwd">return</span><span class="pln"> </span><span class="kwd">new</span><span class="pln"> </span><span class="typ">Array</span><span class="pun">.</span><span class="typ">ArrayEnumerator</span><span class="pun">(</span><span class="kwd">this</span><span class="pun">,</span><span class="pln"> lowerBound</span><span class="pun">,</span><span class="pln"> </span><span class="kwd">this</span><span class="pun">.</span><span class="typ">Length</span><span class="pun">);</span><span class="pln">
</span><span class="pun">}</span>

List:

<span class="com">// System.Collections.Generic.List</span><span class="pln">
</span><span class="kwd">public</span><span class="pln"> </span><span class="typ">List</span><span class="pun">.</span><span class="typ">Enumerator</span><span class="pln"> </span><span class="typ">GetEnumerator</span><span class="pun">()</span><span class="pln">
</span><span class="pun">{</span><span class="pln">
</span><span class="kwd">return</span><span class="pln"> </span><span class="kwd">new</span><span class="pln"> </span><span class="typ">List</span><span class="pun">.</span><span class="typ">Enumerator</span><span class="pun">(</span><span class="kwd">this</span><span class="pun">);</span><span class="pln">
</span><span class="pun">}</span>

Dictionary:

<span class="com">// System.Collections.Generic.Dictionary</span><span class="pln">
</span><span class="kwd">public</span><span class="pln"> </span><span class="typ">Dictionary</span><span class="pun">.</span><span class="typ">Enumerator</span><span class="pln"> </span><span class="typ">GetEnumerator</span><span class="pun">()</span><span class="pln">
</span><span class="pun">{</span><span class="pln">
</span><span class="kwd">return</span><span class="pln"> </span><span class="kwd">new</span><span class="pln"> </span><span class="typ">Dictionary</span><span class="pun">.</span><span class="typ">Enumerator</span><span class="pun">(</span><span class="kwd">this</span><span class="pun">,</span><span class="pln"> </span><span class="lit">2</span><span class="pun">);</span><span class="pln">
</span><span class="pun">}</span>

 

从以上代码来看,我们再进行foreach操作以上对象的时候都会构建一个Enumerator;也许有人会认为这点东西不需要计较,不过的确 很多情况是不用关心;但如果通过内存分析到到的结果表明构建Enumerator的数量排在前几位,那就真的要关心一下了。很简单的一个应用假设你的应用 要处理几W的并发,而每次都存在几次foreach那你就能计算出有多少对象的产生和回收?看下一个简单的分析图,这里紧紧是存在一个List’1如果组 件内部每个并发多几个foreach又会怎样?

改成for的结果又怎样呢

赞(0) 打赏
分享到: 更多 (0)

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

微信扫一扫打赏

登录

注册