Sunday, April 7, 2013

Lazy Evaluation And Infinite Data Structures In C#

Today I was reading the "Functional programming with Haskell" tutorial by Rob Harrop. In this article Rob also shows the ability of Haskell to handle the so called Infinite Data Structures using an infinite list of prime numbers as an example. The author defines infinite data structures as "data structures that abstract the details of some infinite stream of data". Due to Haskells support for lazy evaluation such infinite lists can be treated like normal lists. While reading the article I was wondering if I can do the same thing in C#. Though it's an eagerly evalutated language (means: the expression gets evaluated as soon as you assign it to a variable) using the yield keyword you can deal with infinite data structures:
public class Primes {
  public IEnumerable<int> All () {
    int number = 2;
    while (true) {
      while (!IsPrime (number)) ++number;
      yield return number++;
    }
  }

  public bool IsPrime (int number) {
    if(number < 3) return true;
    var seq = Enumerable.Range (2, number - 2);
    Func<int, int, bool> divides = (n,p) => n % p == 0;
    return seq.All(p => !divides (number, p));
  }
}
The Primes.All() method returns an "infinite" list of prime numbers. Thank to the yield keyword the numbers are not computed until you really use them, e.g. you can get the first ten prime numbers by:
var primes = new Primes ();
var firstTenPrimes = primes.All().Take(10);
With the power of the LINQ framework the Primes.All() method even becomes a "one liner":
public IEnumerable<int> All () {
  return Enumerable.Range (2, int.MaxValue - 1)
                   .Where (IsPrime);
}
I really like these functional features in C# :)