Implementing foreach-else for .Net (C#)

Jan. 9, 2011, 1:33 a.m.

I like the idea of having else-branches for loops as Python supports them for its for and while statements. It allows code like this:

for i in range(2, n):
    if n % i == 0:
        print n, 'equals', i, '*', n / i
        break
else:
    print n, 'is a prime'

else is executed after the loop, unless the loop is terminated by a break statement. Pretty handy, I think. I've decided this is awesome enough to justify the following extension method:

public static void ForEachElse<TSource>(
    this IEnumerable<TSource> source,
    Func<TSource, bool> action, Action @else)
{
    foreach (var i in source)
    {
        if (!action(i))
        {
            return;
        }
    }
    @else();
}

It's your regular every day foreach on IEnumerable but allows you to specify both a "loop-action" and an "else-action" where the latter is executed after the loop unless you break the loop by returning false from the former. It's a tad clumsier than Python but still useful:

Enumerable.Range(2, n - 2).ForEachElse(i =>
{
    if (n % i == 0)
    {
        Console.WriteLine("{0} equals {1} * {2}", n, i, n / i);
        return false; // break
    }
    return true; // continue
},
() => // else
{
    Console.WriteLine("{0} is a prime", n);
});

What do you think? Implementing WhileElse is left as an exercise to the reader :)

about