(原) “线程池”的一个小例子
/*
* “线程池”是可以用来在后台执行多个任务的线程集合。
* 线程池通常具有最大线程数限制。如果所有线程都繁忙,则额外的任务将放入队列中,直到有线程可用时才能够得到处理。
* ThreadPool.QueueUserWorkItem: 将用户方法排入队列以便执行。此方法在有线程池线程变得可用时执行。
* ManualResetEven: 通知一个或多个正在等待的线程已发生事件。_doneEvent.Set() 将事件状态设置为终止状态
* 当计算完成时,每个对象都通知提供的事件对象,使主线程用 WaitAll 阻止执行,直到十个 Fibonacci 对象全部计算出了结果。
* EventWaitHandle表示一个线程同步事件。WaitHandle封装等待对共享资源的独占访问的操作系统特定的对象。
* ManualResetEven 继承于 EventWaitHandle,EventWaitHandle 继承于 WaitHandle
* 考虑1:如何获取哪个任务已经完成? if _doneEvent.Set(); then event end.
* 考虑2:如何获取事件的状态。ManualResetEvent 哪个属性使我们了解这个事件已经结束?请高手回答。
*/
namespace FibonacciPool11
{
using System;
using System.Threading;
// Fibonacci
public class Fibonacci
{
private int _n;
private int _fibOfN;
private ManualResetEvent _doneEvent;
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("thead {0} result calculated", threadIndex);
_doneEvent.Set(); // 将事件状态设置为终止状态,允许一个或多个等待线程继续
Console.WriteLine("thead {0} ,Fibonacci ({1}) = {2}", threadIndex,_n, _fibOfN); // 事件终止后显示结果
}
// 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);
}
// Properties
public int N { get { return _n; } }
public int FibOfN { get { return _fibOfN; } }
}
class Program
{
static void Main(string[] args)
{
const int FibonacciCalculations = 10;
// One event is used for each Fibonacci object
ManualResetEvent[] doneEvents = new ManualResetEvent[FibonacciCalculations];
Fibonacci[] fibArray = new Fibonacci[FibonacciCalculations];
Random r = new Random();
// Configure and launch 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(10, 30),doneEvents[i]);
fibArray[i] = f;
ThreadPool.QueueUserWorkItem(f.ThreadPoolCallback, i); // 任务入队
}
// Wait for all theads in pool to calculation
WaitHandle.WaitAll(doneEvents); // 等待所有的元素都收到信号
Console.WriteLine("All calculations are complete.");
// Disply the results
for (int i = 0; i < FibonacciCalculations; i++)
{
Fibonacci f = fibArray[i];
Console.WriteLine("Fibonacci ({0}) = {1}", f.N, f.FibOfN);
}
// waiting
Console.ReadLine();
}
}
}
* “线程池”是可以用来在后台执行多个任务的线程集合。
* 线程池通常具有最大线程数限制。如果所有线程都繁忙,则额外的任务将放入队列中,直到有线程可用时才能够得到处理。
* ThreadPool.QueueUserWorkItem: 将用户方法排入队列以便执行。此方法在有线程池线程变得可用时执行。
* ManualResetEven: 通知一个或多个正在等待的线程已发生事件。_doneEvent.Set() 将事件状态设置为终止状态
* 当计算完成时,每个对象都通知提供的事件对象,使主线程用 WaitAll 阻止执行,直到十个 Fibonacci 对象全部计算出了结果。
* EventWaitHandle表示一个线程同步事件。WaitHandle封装等待对共享资源的独占访问的操作系统特定的对象。
* ManualResetEven 继承于 EventWaitHandle,EventWaitHandle 继承于 WaitHandle
* 考虑1:如何获取哪个任务已经完成? if _doneEvent.Set(); then event end.
* 考虑2:如何获取事件的状态。ManualResetEvent 哪个属性使我们了解这个事件已经结束?请高手回答。
*/
namespace FibonacciPool11
{
using System;
using System.Threading;
// Fibonacci
public class Fibonacci
{
private int _n;
private int _fibOfN;
private ManualResetEvent _doneEvent;
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("thead {0} result calculated", threadIndex);
_doneEvent.Set(); // 将事件状态设置为终止状态,允许一个或多个等待线程继续
Console.WriteLine("thead {0} ,Fibonacci ({1}) = {2}", threadIndex,_n, _fibOfN); // 事件终止后显示结果
}
// 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);
}
// Properties
public int N { get { return _n; } }
public int FibOfN { get { return _fibOfN; } }
}
class Program
{
static void Main(string[] args)
{
const int FibonacciCalculations = 10;
// One event is used for each Fibonacci object
ManualResetEvent[] doneEvents = new ManualResetEvent[FibonacciCalculations];
Fibonacci[] fibArray = new Fibonacci[FibonacciCalculations];
Random r = new Random();
// Configure and launch 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(10, 30),doneEvents[i]);
fibArray[i] = f;
ThreadPool.QueueUserWorkItem(f.ThreadPoolCallback, i); // 任务入队
}
// Wait for all theads in pool to calculation
WaitHandle.WaitAll(doneEvents); // 等待所有的元素都收到信号
Console.WriteLine("All calculations are complete.");
// Disply the results
for (int i = 0; i < FibonacciCalculations; i++)
{
Fibonacci f = fibArray[i];
Console.WriteLine("Fibonacci ({0}) = {1}", f.N, f.FibOfN);
}
// waiting
Console.ReadLine();
}
}
}
posted on 2007-12-31 13:26 mjgforever 阅读(539) 评论(0) 编辑 收藏 举报