Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to use wait handles in C# threading?

I have three threads in my program and I want that when thread one finishes it signals thread 2 to start and when thread 2 finishes it should signal thread 3 to start.

How can I achieve this, I know there are wait handles to do that in C#, but I don't know how to use them ?

Following is the code of my program:

class Program
    {
        static void Main(string[] args)
        {
            Thread t1 = new Thread(Task1);
            Thread t2 = new Thread(Task2);
            Thread t3 = new Thread(Task3);

            t1.Start();
            t2.Start();
            t3.Start();

            Console.Read();
        }

        public static void Task1()
        {
            Console.WriteLine("I am assigned task 1:");
            for (int i = 0; i < 50; i++)
            {
                Console.WriteLine("Task1" );
            }
        }
        public static void Task2()
        {
            Console.WriteLine("I am assigned task 2:");
            for (int i = 0; i < 50; i++)
            {
                Console.WriteLine("Task2");
            }
        }
        public static void Task3()
        {
            Console.WriteLine("I am assigned task 3:");
            for (int i = 0; i < 50; i++)
            {
                Console.WriteLine("Task3");
            }
        }
    }
like image 537
Embedd_0913 Avatar asked Dec 05 '25 16:12

Embedd_0913


2 Answers

You need to pass events into the threaded functions that indicate what to signal when each one has finished and what to wait on before they run. Take a look at the (untested) code below to see what I mean:

class Program
    {
        static void Main(string[] args)
        {
            Thread t1 = new Thread(Task1);
            ManualResetEvent e1=new ManualResetEvent(false);

            Thread t2 = new Thread(Task2);
            ManualResetEvent e2=new ManualResetEvent(false);

            Thread t3 = new Thread(Task3);
            ManualResetEvent e3=new ManualResetEvent(false);

            t1.Start(()=>Task1(e1));
            t2.Start(()=>Task2(e1,e2));
            t3.Start(()=>Task3(e2,e3);

            Console.Read();

            t1.Join();
            t2.Join();
            t3.Join();
        }

        public static void Task1(EventWaitHandle handle)
        {
            Console.WriteLine("I am assigned task 1:");
            for (int i = 0; i < 50; i++)
            {
                Console.WriteLine("Task1" );
            }
            handle.Set();

        }
        public static void Task2(EventWaitHandle waitFor, EventWaitHandle handle)
        {
            waitFor.WaitOne();

            Console.WriteLine("I am assigned task 2:");
            for (int i = 0; i < 50; i++)
            {
                Console.WriteLine("Task2");
            }

            handle.Set();
        }
        public static void Task3(EventWaitHandle waitFor, EventWaitHandle handle)
        {
            waitFor.WaitOne();

            Console.WriteLine("I am assigned task 3:");
            for (int i = 0; i < 50; i++)
            {
                Console.WriteLine("Task3");
            }

            handle.Set();
        }
    }
like image 115
Sean Avatar answered Dec 08 '25 06:12

Sean


It appears that you want to run Tasks 1 - 3 to execute synchronously. So, you might as well do:

Task1();
Task2();
Task3();

If you want to offload the execution of these tasks to another thread, you can do:

static void RunTasks()
{
    Task1();
    Task2();
    Task3();
}

static void Main()
{
   new Thread(RunTasks).Start();
}

If you really wanted each task to run on a separate thread, and wait for the previous task to finish, you can use the Thread.Join method.

EDIT:

Since you really want to use wait-handles to accomplish this, take a look at the ManualResetEvent class.

Notifies one or more waiting threads that an event has occurred.

Call the WaitOne method on it to wait on the event, and the Set method to signal it.

Example (horribly contrived code):

var afterT1Event = new ManualResetEvent(false);
var afterT2Event = new ManualResetEvent(false);

Thread t1 = new Thread(() => { Task1(); afterT1Event.Set(); });
Thread t2 = new Thread(() => { afterT1Event.WaitOne(); Task2(); afterT2Event.Set(); });
Thread t3 = new Thread(() => { afterT2Event.WaitOne(); Task3(); });

t1.Start();
t2.Start();
t3.Start();
like image 35
Ani Avatar answered Dec 08 '25 07:12

Ani



Donate For Us

If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!