티스토리 뷰

C#

ThreadPool with WaitHandle

갱생쌩유 2015. 9. 17. 17:34

원래 중점 이슈는 WaitHandle.WaitAll(WaitHandle[]) 함수의 파라미터 변수 값의 64개 제한이었다.
64개의 제한 없이 모든 쓰레드의 처리를 기다린 후 뒤이어 진행을 바랬던 생각에서 파라미터 변수의 제한때문에
알아본 바를 기록한다.

대안은 WaitHandle(AutoResetEvent, ManualResetEvent)의 Set() 과 WaitOne() 의 사용.

ThreadPool 에서 사용하는 함수에서 WaitHandle 의 Set() 을 처리해 주고
주 스레드에서 WaitOne() 을 처리해 주는 형식.


# 첨부 소스

public class Fibonacci
    {
        private int _n;
        private int _fibOfN;
        private ManualResetEvent _doneEvent;
        private int _numerOfThreadsNotYetCompleted = 1;

        public int N { get { return _n; } }
        public int FibOfN { get { return _fibOfN; } }

        // Constructor.
        public Fibonacci(int n, ManualResetEvent doneEvent)
        {
            _n = n;
            _doneEvent = doneEvent;
        }

        // Wrapper method for use with thread pool.
        public void ThreadPoolCallback(Object threadContext)
        {
            int threadIndex = (int)threadContext;
            Console.WriteLine("thread {0} started...", threadIndex);
            _fibOfN = Calculate(_n);
            Console.WriteLine("thread {0} result calculated...", threadIndex);

            // 스레드가 완료하면 현재 스레드가 완료되었다고 신호를 줍니다.
            _doneEvent.Set();
        }

        // Recursive method that calculates the Nth Fibonacci number.
        public int Calculate(int n)
        {
            if (n <= 1)
            {
                return n;
            }

            return Calculate(n - 1) + Calculate(n - 2);
        }
    }

    class Program
    {
        static void Main(string[] args)
        {
            const int FibonacciCalculations = 100000;

            // One event is used for each Fibonacci object.
            ManualResetEvent[] doneEvents = new ManualResetEvent[FibonacciCalculations];
            Fibonacci[] fibArray = new Fibonacci[FibonacciCalculations];
            Random r = new Random();

            // Configure and start threads using ThreadPool.
            Console.WriteLine("launching {0} tasks...", FibonacciCalculations);
            for (int i = 0; i < FibonacciCalculations; i++)
            {
                doneEvents[i] = new ManualResetEvent(false);
                Fibonacci f = new Fibonacci(r.Next(1, 20), doneEvents[i]);
                fibArray[i] = f;
               
                // 스레드 풀에 수행할 작업을 입력합니다.
                ThreadPool.QueueUserWorkItem(f.ThreadPoolCallback, i);
                //doneEvents[i].WaitOne();
            }

            foreach (var done in doneEvents)
            {
                done.WaitOne();
            }

            // 스레드 풀에 있는 스레드 작업이 완료 될때까지 대기합니다.
            // 모든 스레드가 완료 되었다는 신호를 받으면 결과값을 보여줍니다.
            //WaitHandle.WaitAll(doneEvents);
            Console.WriteLine("All calculations are complete.\r\n\r\n");

            // Display the results.
            for (int i = 0; i < FibonacciCalculations; i++)
            {
                Fibonacci f = fibArray[i];
                Console.WriteLine("Fibonacci({0}) = {1}", f.N, f.FibOfN);
            }

            Console.ReadLine();
        }
    }


공지사항
최근에 올라온 글
최근에 달린 댓글
Total
Today
Yesterday
링크
«   2026/04   »
1 2 3 4
5 6 7 8 9 10 11
12 13 14 15 16 17 18
19 20 21 22 23 24 25
26 27 28 29 30
글 보관함