locked
Break out of Parallel.Foreach in June CTP RRS feed

  • Question

  • How do you break out of a Parallel.Foreach loop in the June CTP? I see that in the .NET 4.0 extensions they have added the ability to do so, but how do you do it in the previous set of extensions?
    Thursday, September 24, 2009 8:27 PM

Answers

  • ParallelState is public; its constructor is internal.  But you don't need to construct one.  Rather, the loop constructs one and passes that instance in to your delegate, e.g.

    using System;
    using System.Threading;
    
    class Program
    {
        static void Main(string[] args)
        {
            int[] data = new int[] { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10 };
            Parallel.ForEach(data, (i, state) =>
            {
                if (i == 4) state.Stop();
                Thread.Sleep(i * 1000);
                Console.WriteLine(i);
            });
        }
    }
    Saturday, September 26, 2009 12:09 AM
    Moderator

All replies

  • The June CTP supported this by using an overload of Parallel.ForEach that used a delegate which accepted a ParallelState parameter.  That ParallelState exposed a Stop method, which could be used to exit a loop early.  Throwing an exception would also cause early exit from a loop.
    Friday, September 25, 2009 1:07 AM
    Moderator
  • But the problem is that the ParallelState enumeration is marked as internal. AFAICT, there is no way to create an instance of it.
    Friday, September 25, 2009 4:57 PM
  • ParallelState is public; its constructor is internal.  But you don't need to construct one.  Rather, the loop constructs one and passes that instance in to your delegate, e.g.

    using System;
    using System.Threading;
    
    class Program
    {
        static void Main(string[] args)
        {
            int[] data = new int[] { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10 };
            Parallel.ForEach(data, (i, state) =>
            {
                if (i == 4) state.Stop();
                Thread.Sleep(i * 1000);
                Console.WriteLine(i);
            });
        }
    }
    Saturday, September 26, 2009 12:09 AM
    Moderator
  • Ah. Using a undeclared variable called "state" seemingly out of thin-air is definitely not intuitive but with multi-threaded development that seems to be par for the course ;->. Thanks!
    Saturday, September 26, 2009 12:14 AM
  • Happy to help.

    I'm using the most condensed lambda syntax.  If it helps from a clarity perspective, you could expand it to the full delegate syntax:

    Parallel.ForEach(data, delegate(int i, ParallelState state)
    {
         ...
    });

    or even separating out the delegate:

    Action<int, ParallelState> body = delegate(int i, ParallelState state)
    {
        ...
    });
    Parallel.ForEach(data, body);

    Finally, of course, you can separate the body out into its own method.
    Saturday, September 26, 2009 12:33 AM
    Moderator