Home > Refactorings > The Introduce ForEach Action refactoring

The Introduce ForEach Action refactoring

August 28th, 2012

It is a rather trivial task to iterate over each item of the generic List using a foreach-loop as follows:

ForEach-loop iteration

However, you might be aware that the generic list has its own ForEach method which performs the specified operation (Action) on each element of the list:

ForEach Call iteration

So, what’s the difference between these two methods of iterating list items? Let’s find out.

The first difference is that the foreach-loop does not allow you to modify the state by adding or removing items while iterating over the collection. But with the List.ForEach call you can modify the underlying collection without questions asked, where as with the foreach syntax, you’ll get an exception if you do that.

The second difference is about performance. Let’s compare the standard foreach-loop and the ForEach call on the generic list with the following block of code:

CodeRush Introduce ForEach Action code sample

To convert this code into a ForEach call, the Introduce ForEach Action refactoring can be used:

CodeRush Introduce ForEach Action preview

that will produce the required code automatically once applied:

CodeRush Introduce ForEach Action result

Now, we can test both list-iteration methods in a test application with a different number of iterations. I got the following results on my machine (Core2 Duo T7250 @2.00Ghz, 3.00Gb RAM):

Number of iterations

foreach-loop

List<int>.ForEach

1,000

0.000021

0.000015

5,000

0.000082

0.000049

10,000

0.000156

0.000094

50,000

0.000786

0.000510

100,000

0.001551

0.000889

500,000

0.007299

0.004454

1,000,000

0.014920

0.008751

5,000,000

0.072565

0.043666

10,000,000

0.145069

0.087591

According to this result, it turns out that the ForEach call is much faster than the default foreach-loop. However, this result is taken without the ‘Optimize code’ build option set. If we turn it on, we will get the following result:

# iterations

foreach-loop

List<int>.ForEach

1,000

0.000016

0.000013

5,000

0.000062

0.000045

10,000

0.000119

0.000084

50,000

0.000555

0.000322

100,000

0.001113

0.000790

500,000

0.005541

0.003921

1,000,000

0.011354

0.007964

5,000,000

0.055643

0.038843

10,000,000

0.112101

0.078943

If we compare two results, we see that the foreach-loop gets optimized in about 23%, but the ForEach does not receive as much optimization. However, the ForEach call is still faster than the foreach-loop, whether the code is optimized or not. Let’s take a look at the picture illustrating the results:

ForEach-loop VS ForEach call

So, the ForEach might be preferred in performance critical code blocks. If you’d like to convert the existing foreach-loop iterating over the generic list, consider using the Introduce ForEach Action refactoring which will convert the foreach-loop quickly.

—–
Products: CodeRush Pro
Versions: 12.1 and up
VS IDEs: 2008 and up
Updated: Aug/28/2012
ID: R066

Similar Posts:

  1. August 20th, 2013 at 05:44 | #1

    Hey there, found out why it is slower. If you decompile the code, using ILSpy, you will see that the slower foreach is doing a try catch for the iterator, because it uses IEnumberables. It does not do this for the extension method foreach. Interesting find :-)