Oct 5, 2013

Closures in C#


Hi

Given the following code:

using System;
using System.Collections.Generic;
using System.Linq;

class Program
{
   private static void Main(string[] args)
   {
      foreach (var func in GetFuncs1())
      {
         Console.WriteLine("[first] {0}", func());
      }

      foreach (var func in GetFuncs2())
      {
         Console.WriteLine("[second] {0}", func());
      }
   }

   private static List<Func<int>> GetFuncs1()
   {
      var fs = new List<Func<int>>();

      for (int i = 0; i < 3; i++)
      {
         fs.Add(() => i);
      }
      return fs;
   }

   private static List<Func<int>> GetFuncs2()
   {
      var fs = new List<Func<int>>();

      foreach (var i in Enumerable.Range(0, 3))
      {
         fs.Add(() => i);
      }
      return fs;
    }  
}

What do you expect as the output? (try answering before running it)

Does it produces the results you expected? No? Do you understand why?

(If you are using Resharper it will warn you that you wrote code that captures variables and can produce "unexpected" results)

In the next post I'll give the answer and discuss it.

Happy coding.

(leia este post em Português)

No comments: