衔接UI线程和管理后台工作线程的类(多线程、异步调用)

一、引言
     在编写Windows form时,如果直接在UI线程要运行一个费时方法的话(如从数据库查询大量数据时),会引起程序“假死”,从而导致用户不满。这个时候就需要通过多线程技术来解决,提高界面交互性能,方便用户使用。
一般通过三种方式解决:
1.通过System.Threading.Thread类,创建新的线程,Thread.Start运行费时方法。
2.通过System.Threading.ThreadPool类,将费时任务提交到线程池中,等待运行。
以上两种方法,基本思路是在UI界面中控制线程的启动和中止,在线程中回调用UI界面方法,更新界面。在线程中回调UI界面方法时,特别是涉及更新控件属性时,如果不注意,存在很大的隐患。这两种办法,编码和控制结构较为复杂,需要启动和管理额外的线程占用资源。
3.通过异步委托调用,将该方法排队到系统线程池的线程中运行,而在费时方法中也通过Control.BeginInvoke异步回调,达到"启动后不管"的目的。
这种方法,编码简单,程序结构较为清晰,充分利用.NET框架的异步委托功能,但要对异步调用知识较熟悉。
相关知识点参见
     现利用.NET异步委托调用功能,编写Task抽象类,以方便管理后台工作线程,衔接后台线程与UI线程的联系。该抽象类提供了调用和管理的框架,没有方法的实现细节,通过继承类、重写方法,可以实现想要的功能。主要功能如下:
1.利用异步委托调用,实际多线程,不需要单独后台线程。
2.通过委托、事件驱动,实际后台与前台UI线程的联系,实现事件广播。
3.支持正常取消后台工作方法(费时方法)运行,也可以强制中止线程。
4.能够捕获取消、强制中止和方法出错三种情况,并突发相关事件,以便进行释放资源等操作。
5.通过异步调用,在工作方法中安全调用涉及UI控件的方法。
6.自行管理工作进程状态,提供状态变化事件。
7.只要工作方法调用签名,符合定义的TaskDelegate委托接口,可通过StartTask(TaskDelegate worker ,params object[] args )方便调用。在实际使用时,可在继承类中定义多个相同调用接口的方法,避免重复编码,较为方便。

给大家作个参考,而大牛呢,多点指正。当是扔个砖头,想砸块玉吧。


二、代码

  1 None.gif using  System;
  2 None.gif using  System.Windows.Forms;
  3 None.gif
  4 None.gif namespace  Net66.AsynchThread
  5 ExpandedBlockStart.gifContractedBlock.gif dot.gif {
  6ExpandedSubBlockStart.gifContractedSubBlock.gif    /**//// <summary>
  7InBlock.gif    /// 任务工作状态
  8ExpandedSubBlockEnd.gif    /// </summary>

  9InBlock.gif    public enum TaskStatus 
 10ExpandedSubBlockStart.gifContractedSubBlock.gif    dot.gif
 11ExpandedSubBlockStart.gifContractedSubBlock.gif        /**//// <summary>
 12InBlock.gif        /// 任务没有运行,可能是工作进程没有开始、工作进程正常结束或正常取消工作进程
 13ExpandedSubBlockEnd.gif        /// </summary>

 14InBlock.gif        Stopped, 
 15ExpandedSubBlockStart.gifContractedSubBlock.gif        /**//// <summary>
 16InBlock.gif        /// 任务没有运行,被调用者强行中止
 17ExpandedSubBlockEnd.gif        /// </summary>

 18InBlock.gif        Aborted,
 19ExpandedSubBlockStart.gifContractedSubBlock.gif        /**//// <summary>
 20InBlock.gif        /// 任务没有运行,在工作进程中触发错误而中止
 21ExpandedSubBlockEnd.gif        /// </summary>

 22InBlock.gif        ThrowErrorStoped,
 23ExpandedSubBlockStart.gifContractedSubBlock.gif        /**//// <summary>
 24InBlock.gif        /// 任务运行中
 25ExpandedSubBlockEnd.gif        /// </summary>

 26InBlock.gif        Running, 
 27ExpandedSubBlockStart.gifContractedSubBlock.gif        /**//// <summary>
 28InBlock.gif        /// 尝试取消工作进程中
 29ExpandedSubBlockEnd.gif        /// </summary>

 30InBlock.gif        CancelPending,
 31ExpandedSubBlockStart.gifContractedSubBlock.gif        /**//// <summary>
 32InBlock.gif        /// 强行中止工作进程中
 33ExpandedSubBlockEnd.gif        /// </summary>

 34InBlock.gif        AbortPending
 35InBlock.gif
 36ExpandedSubBlockEnd.gif    }
 
 37InBlock.gif
 38ExpandedSubBlockStart.gifContractedSubBlock.gif    /**//// <summary>
 39InBlock.gif    /// 任务状态消息
 40ExpandedSubBlockEnd.gif    /// </summary>

 41InBlock.gif    public class TaskEventArgs : EventArgs 
 42ExpandedSubBlockStart.gifContractedSubBlock.gif    dot.gif
 43ExpandedSubBlockStart.gifContractedSubBlock.gif        /**//// <summary>
 44InBlock.gif        /// 任务运行结果
 45ExpandedSubBlockEnd.gif        /// </summary>

 46InBlock.gif        public Object     Result; 
 47ExpandedSubBlockStart.gifContractedSubBlock.gif        /**//// <summary>
 48InBlock.gif        /// 任务进度(0-100)
 49ExpandedSubBlockEnd.gif        /// </summary>

 50InBlock.gif        public int        Progress; 
 51ExpandedSubBlockStart.gifContractedSubBlock.gif        /**//// <summary>
 52InBlock.gif        /// 任务工作状态
 53ExpandedSubBlockEnd.gif        /// </summary>

 54InBlock.gif        public TaskStatus Status; 
 55ExpandedSubBlockStart.gifContractedSubBlock.gif        /**//// <summary>
 56InBlock.gif        /// 任务消息文本
 57ExpandedSubBlockEnd.gif        /// </summary>

 58InBlock.gif        public String Message;
 59ExpandedSubBlockStart.gifContractedSubBlock.gif        /**//// <summary>
 60InBlock.gif        /// 创建任务状态消息
 61InBlock.gif        /// </summary>
 62ExpandedSubBlockEnd.gif        /// <param name="progress">任务进度(0-100)</param>

 63InBlock.gif        public TaskEventArgs( int progress ) 
 64ExpandedSubBlockStart.gifContractedSubBlock.gif        dot.gif
 65InBlock.gif            this.Progress = progress; 
 66InBlock.gif            this.Status   = TaskStatus.Running; 
 67ExpandedSubBlockEnd.gif        }
 
 68ExpandedSubBlockStart.gifContractedSubBlock.gif        /**//// <summary>
 69InBlock.gif        /// 创建任务状态消息
 70InBlock.gif        /// </summary>
 71ExpandedSubBlockEnd.gif        /// <param name="status">任务线程状态</param>

 72InBlock.gif        public TaskEventArgs( TaskStatus status ) 
 73ExpandedSubBlockStart.gifContractedSubBlock.gif        dot.gif
 74InBlock.gif            this.Status = status; 
 75ExpandedSubBlockEnd.gif        }
 
 76ExpandedSubBlockStart.gifContractedSubBlock.gif        /**//// <summary>
 77InBlock.gif        /// 创建任务状态消息
 78InBlock.gif        /// </summary>
 79InBlock.gif        /// <param name="progress">任务进度(0-100)</param>
 80ExpandedSubBlockEnd.gif        /// <param name="result">任务运行中间结果</param>

 81InBlock.gif        public TaskEventArgs( int progress,object result ) 
 82ExpandedSubBlockStart.gifContractedSubBlock.gif        dot.gif
 83InBlock.gif            this.Progress = progress; 
 84InBlock.gif            this.Status   = TaskStatus.Running; 
 85InBlock.gif            this.Result   = result;
 86ExpandedSubBlockEnd.gif        }
 
 87ExpandedSubBlockStart.gifContractedSubBlock.gif        /**//// <summary>
 88InBlock.gif        /// 创建任务状态消息
 89InBlock.gif        /// </summary>
 90InBlock.gif        /// <param name="status">任务线程状态</param>
 91ExpandedSubBlockEnd.gif        /// <param name="result">任务运行结果</param>

 92InBlock.gif        public TaskEventArgs( TaskStatus status,object result ) 
 93ExpandedSubBlockStart.gifContractedSubBlock.gif        dot.gif
 94InBlock.gif            this.Status   = status; 
 95InBlock.gif            this.Result   = result;
 96ExpandedSubBlockEnd.gif        }
 
 97ExpandedSubBlockStart.gifContractedSubBlock.gif        /**//// <summary>
 98InBlock.gif        /// 创建任务状态消息
 99InBlock.gif        /// </summary>
100InBlock.gif        /// <param name="status">任务线程状态</param>
101InBlock.gif        /// <param name="message">消息文本</param>
102ExpandedSubBlockEnd.gif        /// <param name="result">任务运行结果</param>

103InBlock.gif        public TaskEventArgs( TaskStatus status,string message ,object result ) 
104ExpandedSubBlockStart.gifContractedSubBlock.gif        dot.gif
105InBlock.gif            this.Status   = status; 
106InBlock.gif            this.Message = message;
107InBlock.gif            this.Result   = result;
108ExpandedSubBlockEnd.gif        }
 
109ExpandedSubBlockStart.gifContractedSubBlock.gif        /**//// <summary>
110InBlock.gif        /// 创建任务状态消息
111InBlock.gif        /// </summary>
112InBlock.gif        /// <param name="progress">任务进度(0-100)</param>
113InBlock.gif        /// <param name="message">消息文本</param>
114ExpandedSubBlockEnd.gif        /// <param name="result">任务运行中间结果</param>

115InBlock.gif        public TaskEventArgs( int progress,string message ,object result ) 
116ExpandedSubBlockStart.gifContractedSubBlock.gif        dot.gif
117InBlock.gif            this.Progress = progress; 
118InBlock.gif            this.Status   = TaskStatus.Running; 
119InBlock.gif            this.Message = message;
120InBlock.gif            this.Result   = result;
121ExpandedSubBlockEnd.gif        }
 
122ExpandedSubBlockStart.gifContractedSubBlock.gif        /**//// <summary>
123InBlock.gif        /// 创建任务状态消息
124InBlock.gif        /// </summary>
125InBlock.gif        /// <param name="status">任务线程状态</param>
126InBlock.gif        /// <param name="progress">任务进度(0-100)</param>
127InBlock.gif        /// <param name="message">消息文本</param>
128ExpandedSubBlockEnd.gif        /// <param name="result">任务运行中间结果</param>

129InBlock.gif        public TaskEventArgs( TaskStatus status,int progress,string message ,object result ) 
130ExpandedSubBlockStart.gifContractedSubBlock.gif        dot.gif
131InBlock.gif            this.Status = status;
132InBlock.gif            this.Progress = progress; 
133InBlock.gif            this.Message = message;
134InBlock.gif            this.Result   = result;
135ExpandedSubBlockEnd.gif        }
 
136ExpandedSubBlockEnd.gif    }
     
137InBlock.gif
138ExpandedSubBlockStart.gifContractedSubBlock.gif    /**//// <summary>
139InBlock.gif    /// 任务的工作方法(Work)的委托接口
140InBlock.gif    /// 传入值:对象数组(object[])
141InBlock.gif    /// 返回值:对象(object)
142ExpandedSubBlockEnd.gif    /// </summary>

143InBlock.gif    public delegate object TaskDelegate( params object[] args ); 
144InBlock.gif
145ExpandedSubBlockStart.gifContractedSubBlock.gif    /**//// <summary>
146InBlock.gif    /// 任务事件的委托接口
147ExpandedSubBlockEnd.gif    /// </summary>

148InBlock.gif    public delegate void TaskEventHandler( object sender, TaskEventArgs e ); 
149InBlock.gif
150InBlock.gif    abstract public class Task
151ExpandedSubBlockStart.gifContractedSubBlock.gif    dot.gif{   
152ExpandedSubBlockStart.gifContractedSubBlock.gif        内部属性#region 内部属性
153ExpandedSubBlockStart.gifContractedSubBlock.gif        /**//// <summary>
154InBlock.gif        /// 任务调用线程(前台或UI线程)
155ExpandedSubBlockEnd.gif        /// </summary>

156InBlock.gif        protected System.Threading.Thread _callThread = null
157ExpandedSubBlockStart.gifContractedSubBlock.gif        /**//// <summary>
158InBlock.gif        /// 任务工作线程(后台)
159ExpandedSubBlockEnd.gif        /// </summary>

160InBlock.gif        protected System.Threading.Thread _workThread = null
161ExpandedSubBlockStart.gifContractedSubBlock.gif        /**//// <summary>
162InBlock.gif        /// 任务工作状态
163ExpandedSubBlockEnd.gif        /// </summary>

164InBlock.gif        protected TaskStatus _taskState = TaskStatus.Stopped; 
165ExpandedSubBlockStart.gifContractedSubBlock.gif        /**//// <summary>
166InBlock.gif        /// 任务进度(0-100)
167ExpandedSubBlockEnd.gif        /// </summary>

168InBlock.gif        protected int _progress = -1;
169ExpandedSubBlockStart.gifContractedSubBlock.gif        /**//// <summary>
170InBlock.gif        /// 任务工作结果
171ExpandedSubBlockEnd.gif        /// </summary>

172InBlock.gif        protected object _result = null;
173ExpandedSubBlockStart.gifContractedSubBlock.gif        /**//// <summary>
174InBlock.gif        /// 任务工作进程出错时,捕获的异常对象
175ExpandedSubBlockEnd.gif        /// </summary>

176InBlock.gif        protected Exception _exception = null;
177ExpandedSubBlockEnd.gif        #endregion

178InBlock.gif
179ExpandedSubBlockStart.gifContractedSubBlock.gif        事件#region 事件
180ExpandedSubBlockStart.gifContractedSubBlock.gif        /**//// <summary>
181InBlock.gif        /// 任务工作状态变化事件
182ExpandedSubBlockEnd.gif        /// </summary>

183InBlock.gif        public event TaskEventHandler TaskStatusChanged; 
184ExpandedSubBlockStart.gifContractedSubBlock.gif        /**//// <summary>
185InBlock.gif        /// 任务进度变化事件
186ExpandedSubBlockEnd.gif        /// </summary>

187InBlock.gif        public event TaskEventHandler TaskProgressChanged; 
188ExpandedSubBlockStart.gifContractedSubBlock.gif        /**//// <summary>
189InBlock.gif        /// 任务被调用者强行中止事件
190ExpandedSubBlockEnd.gif        /// </summary>

191InBlock.gif        public event TaskEventHandler TaskAbort; 
192ExpandedSubBlockStart.gifContractedSubBlock.gif        /**//// <summary>
193InBlock.gif        /// 任务工作方法执行中触发错误事件
194ExpandedSubBlockEnd.gif        /// </summary>

195InBlock.gif        public event TaskEventHandler TaskThrowError; 
196ExpandedSubBlockStart.gifContractedSubBlock.gif        /**//// <summary>
197InBlock.gif        /// 任务被调用者取消事件
198ExpandedSubBlockEnd.gif        /// </summary>

199InBlock.gif        public event TaskEventHandler TaskCancel; 
200ExpandedSubBlockEnd.gif        #endregion

201InBlock.gif
202ExpandedSubBlockStart.gifContractedSubBlock.gif        属性#region 属性
203InBlock.gif        
204ExpandedSubBlockStart.gifContractedSubBlock.gif        /**//// <summary>
205InBlock.gif        /// 任务工作进程出错时,捕获的异常对象
206ExpandedSubBlockEnd.gif        /// </summary>

207InBlock.gif        public Exception Exception
208ExpandedSubBlockStart.gifContractedSubBlock.gif        dot.gif{
209ExpandedSubBlockStart.gifContractedSubBlock.gif            get dot.gifreturn _exception;}
210ExpandedSubBlockEnd.gif        }

211ExpandedSubBlockStart.gifContractedSubBlock.gif        /**//// <summary>
212InBlock.gif        /// 任务调用线程(前台或UI线程)
213ExpandedSubBlockEnd.gif        /// </summary>

214InBlock.gif        public System.Threading.Thread CallThread
215ExpandedSubBlockStart.gifContractedSubBlock.gif        dot.gif{
216ExpandedSubBlockStart.gifContractedSubBlock.gif            get dot.gifreturn _callThread;}
217ExpandedSubBlockEnd.gif        }

218ExpandedSubBlockStart.gifContractedSubBlock.gif        /**//// <summary>
219InBlock.gif        /// 任务工作线程(后台)
220ExpandedSubBlockEnd.gif        /// </summary>

221InBlock.gif        public System.Threading.Thread WordThread
222ExpandedSubBlockStart.gifContractedSubBlock.gif        dot.gif{
223ExpandedSubBlockStart.gifContractedSubBlock.gif            get dot.gif{return _workThread;}
224ExpandedSubBlockEnd.gif        }

225InBlock.gif        
226ExpandedSubBlockStart.gifContractedSubBlock.gif        /**//// <summary>
227InBlock.gif        /// 任务进度(0-100)
228ExpandedSubBlockEnd.gif        /// </summary>

229InBlock.gif        public int Progress
230ExpandedSubBlockStart.gifContractedSubBlock.gif        dot.gif{
231ExpandedSubBlockStart.gifContractedSubBlock.gif            get dot.gif{return _progress;} 
232ExpandedSubBlockEnd.gif        }

233ExpandedSubBlockStart.gifContractedSubBlock.gif        /**//// <summary>
234InBlock.gif        /// 任务工作状态
235ExpandedSubBlockEnd.gif        /// </summary>

236InBlock.gif        public TaskStatus TaskState
237ExpandedSubBlockStart.gifContractedSubBlock.gif        dot.gif{
238ExpandedSubBlockStart.gifContractedSubBlock.gif            get dot.gif{return _taskState;}
239ExpandedSubBlockEnd.gif        }

240ExpandedSubBlockStart.gifContractedSubBlock.gif        /**//// <summary>
241InBlock.gif        /// 任务工作结果
242ExpandedSubBlockEnd.gif        /// </summary>

243InBlock.gif        public object Result
244ExpandedSubBlockStart.gifContractedSubBlock.gif        dot.gif{
245ExpandedSubBlockStart.gifContractedSubBlock.gif            get dot.gif{return _result;}
246ExpandedSubBlockEnd.gif        }

247InBlock.gif
248InBlock.gif        protected bool IsStop
249ExpandedSubBlockStart.gifContractedSubBlock.gif        dot.gif{
250InBlock.gif            get
251ExpandedSubBlockStart.gifContractedSubBlock.gif            dot.gif{
252InBlock.gif                bool result = false;
253InBlock.gif                switch (_taskState)
254ExpandedSubBlockStart.gifContractedSubBlock.gif                dot.gif{
255InBlock.gif                    case TaskStatus.Stopped:
256InBlock.gif                    case TaskStatus.Aborted:
257InBlock.gif                    case TaskStatus.ThrowErrorStoped:
258InBlock.gif                        result = true;
259InBlock.gif                        break;
260InBlock.gif                    default:
261InBlock.gif                        break;
262ExpandedSubBlockEnd.gif                }

263InBlock.gif                return result;
264ExpandedSubBlockEnd.gif            }

265ExpandedSubBlockEnd.gif        }

266ExpandedSubBlockEnd.gif        #endregion

267InBlock.gif
268ExpandedSubBlockStart.gifContractedSubBlock.gif        触发事件#region 触发事件
269ExpandedSubBlockStart.gifContractedSubBlock.gif        /**//// <summary>
270InBlock.gif        /// 触发任务工作状态变化事件
271InBlock.gif        /// </summary>
272InBlock.gif        /// <param name="status">任务工作状态</param>
273ExpandedSubBlockEnd.gif        /// <param name="result">任务工作结果对象</param>

274InBlock.gif        protected void FireStatusChangedEvent(TaskStatus status, object result) 
275ExpandedSubBlockStart.gifContractedSubBlock.gif        dot.gif
276InBlock.gif            if( TaskStatusChanged != null ) 
277ExpandedSubBlockStart.gifContractedSubBlock.gif            dot.gif
278InBlock.gif                TaskEventArgs args = new TaskEventArgs( status,result); 
279InBlock.gif                AsyncInvoke(TaskStatusChanged,args);
280ExpandedSubBlockEnd.gif            }
 
281ExpandedSubBlockEnd.gif        }
 
282InBlock.gif 
283ExpandedSubBlockStart.gifContractedSubBlock.gif        /**//// <summary>
284InBlock.gif        /// 触发任务进度变化事件
285InBlock.gif        /// </summary>
286InBlock.gif        /// <param name="progress">任务进度(0-100)</param>
287ExpandedSubBlockEnd.gif        /// <param name="result">任务工作中间结果对象</param>

288InBlock.gif        protected void FireProgressChangedEvent(int progress, object result) 
289ExpandedSubBlockStart.gifContractedSubBlock.gif        dot.gif
290InBlock.gif            if( TaskProgressChanged != null ) 
291ExpandedSubBlockStart.gifContractedSubBlock.gif            dot.gif
292InBlock.gif                TaskEventArgs args = new TaskEventArgs( progress,result); 
293InBlock.gif                AsyncInvoke(TaskProgressChanged,args);
294ExpandedSubBlockEnd.gif            }
 
295ExpandedSubBlockEnd.gif        }
 
296ExpandedSubBlockStart.gifContractedSubBlock.gif        /**//// <summary>
297InBlock.gif        /// 触发工作方法执行中发现错误事件
298InBlock.gif        /// </summary>
299InBlock.gif        /// <param name="progress">任务进度(0-100)</param>
300ExpandedSubBlockEnd.gif        /// <param name="result">任务工作中间结果对象</param>

301InBlock.gif        protected void FireThrowErrorEvent(int progress, object result) 
302ExpandedSubBlockStart.gifContractedSubBlock.gif        dot.gif
303InBlock.gif            if( TaskThrowError != null ) 
304ExpandedSubBlockStart.gifContractedSubBlock.gif            dot.gif
305InBlock.gif                TaskEventArgs args = new TaskEventArgs( progress,result); 
306InBlock.gif                AsyncInvoke(TaskThrowError,args);
307ExpandedSubBlockEnd.gif            }
 
308ExpandedSubBlockEnd.gif        }
 
309ExpandedSubBlockStart.gifContractedSubBlock.gif        /**//// <summary>
310InBlock.gif        /// 触发被调用者取消事件
311InBlock.gif        /// </summary>
312InBlock.gif        /// <param name="progress">任务进度(0-100)</param>
313ExpandedSubBlockEnd.gif        /// <param name="result">任务工作中间结果对象</param>

314InBlock.gif        protected void FireCancelEvent(int progress, object result) 
315ExpandedSubBlockStart.gifContractedSubBlock.gif        dot.gif
316InBlock.gif            if( TaskCancel != null ) 
317ExpandedSubBlockStart.gifContractedSubBlock.gif            dot.gif
318InBlock.gif                TaskEventArgs args = new TaskEventArgs( progress,result); 
319InBlock.gif                AsyncInvoke(TaskCancel,args);
320ExpandedSubBlockEnd.gif            }
 
321ExpandedSubBlockEnd.gif        }
 
322ExpandedSubBlockStart.gifContractedSubBlock.gif        /**//// <summary>
323InBlock.gif        /// 触发被调用者强行中止事件
324InBlock.gif        /// </summary>
325InBlock.gif        /// <param name="progress">任务进度(0-100)</param>
326ExpandedSubBlockEnd.gif        /// <param name="result">任务工作中间结果对象</param>

327InBlock.gif        protected void FireAbortEvent(int progress, object result) 
328ExpandedSubBlockStart.gifContractedSubBlock.gif        dot.gif
329InBlock.gif            if( TaskAbort != null ) 
330ExpandedSubBlockStart.gifContractedSubBlock.gif            dot.gif
331InBlock.gif                TaskEventArgs args = new TaskEventArgs( progress,result); 
332InBlock.gif                AsyncInvoke(TaskAbort,args);
333ExpandedSubBlockEnd.gif            }
 
334ExpandedSubBlockEnd.gif        }
 
335ExpandedSubBlockStart.gifContractedSubBlock.gif        /**//// <summary>
336InBlock.gif        /// 异步调用挂接事件委托
337InBlock.gif        /// </summary>
338InBlock.gif        /// <param name="eventhandler">事件处理方法句柄</param>
339ExpandedSubBlockEnd.gif        /// <param name="args">事件消息</param>

340InBlock.gif        protected void AsyncInvoke(TaskEventHandler eventhandler,TaskEventArgs args)
341ExpandedSubBlockStart.gifContractedSubBlock.gif        dot.gif{
342InBlock.gif//            TaskEventHandler[] tpcs = (TaskEventHandler[])eventhandler.GetInvocationList();
343InBlock.gif            Delegate[] tpcs = eventhandler.GetInvocationList();
344InBlock.gif            foreach(TaskEventHandler tpc in tpcs)
345ExpandedSubBlockStart.gifContractedSubBlock.gif            dot.gif{
346InBlock.gif                if ( tpc.Target is System.Windows.Forms.Control ) 
347ExpandedSubBlockStart.gifContractedSubBlock.gif                dot.gif
348InBlock.gif                    Control targetForm = tpc.Target as System.Windows.Forms.Control; 
349ExpandedSubBlockStart.gifContractedSubBlock.gif                    targetForm.BeginInvoke( tpc,new object[] dot.gifthis, args } ); 
350ExpandedSubBlockEnd.gif                }
 
351InBlock.gif                else 
352ExpandedSubBlockStart.gifContractedSubBlock.gif                dot.gif
353InBlock.gif                    tpc.BeginInvoke(this, args ,null,null); //异步调用,启动后不管
354ExpandedSubBlockEnd.gif                }

355ExpandedSubBlockEnd.gif            }
        
356ExpandedSubBlockEnd.gif        }

357ExpandedSubBlockEnd.gif        #endregion

358InBlock.gif
359ExpandedSubBlockStart.gifContractedSubBlock.gif        工作进程管理#region 工作进程管理
360ExpandedSubBlockStart.gifContractedSubBlock.gif        /**//// <summary>
361InBlock.gif        /// 开启任务默认的工作进程
362InBlock.gif        /// [public object Work(params  object[] args )]
363InBlock.gif        /// </summary>
364ExpandedSubBlockEnd.gif        /// <param name="args">传入的参数数组</param>

365InBlock.gif        public bool StartTask( params object[] args ) 
366ExpandedSubBlockStart.gifContractedSubBlock.gif        dot.gif
367InBlock.gif            return StartTask(new TaskDelegate( Work ),args); 
368ExpandedSubBlockEnd.gif        }
 
369ExpandedSubBlockStart.gifContractedSubBlock.gif        /**//// <summary>
370InBlock.gif        /// 开启任务的工作进程
371InBlock.gif        /// 将开启符合TaskDelegate委托接口的worker工作方法
372InBlock.gif        /// </summary>
373InBlock.gif        /// <param name="worker">工作方法</param>
374ExpandedSubBlockEnd.gif        /// <param name="args">传入的参数数组</param>

375InBlock.gif        public bool StartTask(TaskDelegate worker ,params object[] args ) 
376ExpandedSubBlockStart.gifContractedSubBlock.gif        dot.gif
377InBlock.gif            bool result =false;
378InBlock.gif            lockthis ) 
379ExpandedSubBlockStart.gifContractedSubBlock.gif            dot.gif
380InBlock.gif                if( IsStop && worker != null ) 
381ExpandedSubBlockStart.gifContractedSubBlock.gif                dot.gif
382InBlock.gif                    _result = null;
383InBlock.gif                    _callThread = System.Threading.Thread.CurrentThread;
384InBlock.gif                    // 开始工作方法进程,异步开启,传送回调方法
385InBlock.gif                    worker.BeginInvoke( args ,new AsyncCallback( EndWorkBack ), worker ); 
386InBlock.gif                    // 更新任务工作状态
387InBlock.gif                    _taskState = TaskStatus.Running; 
388InBlock.gif                    // 触发任务工作状态变化事件
389InBlock.gif                    FireStatusChangedEvent( _taskState, null); 
390InBlock.gif                    result = true;
391ExpandedSubBlockEnd.gif                }
 
392ExpandedSubBlockEnd.gif            }
 
393InBlock.gif            return result;
394ExpandedSubBlockEnd.gif        }
 
395ExpandedSubBlockStart.gifContractedSubBlock.gif        /**//// <summary>
396InBlock.gif        /// 请求停止任务进程
397InBlock.gif        /// 是否停止成功,应看任务工作状态属性TaskState是否为TaskStatus.Stop
398ExpandedSubBlockEnd.gif        /// </summary>

399InBlock.gif        public bool StopTask() 
400ExpandedSubBlockStart.gifContractedSubBlock.gif        dot.gif
401InBlock.gif            bool result =false;
402InBlock.gif            lockthis ) 
403ExpandedSubBlockStart.gifContractedSubBlock.gif            dot.gif
404InBlock.gif                if( _taskState == TaskStatus.Running ) 
405ExpandedSubBlockStart.gifContractedSubBlock.gif                dot.gif
406InBlock.gif                    // 更新任务工作状态 
407InBlock.gif                    _taskState = TaskStatus.CancelPending; 
408InBlock.gif                    // 触发任务工作状态变化事件
409InBlock.gif                    FireStatusChangedEvent( _taskState, _result); 
410InBlock.gif                    result = true;
411ExpandedSubBlockEnd.gif                }
 
412ExpandedSubBlockEnd.gif            }
 
413InBlock.gif            return result;
414ExpandedSubBlockEnd.gif        }
 
415ExpandedSubBlockStart.gifContractedSubBlock.gif        /**//// <summary>
416InBlock.gif        /// 强行中止任务的工作线程
417InBlock.gif        /// 
418ExpandedSubBlockEnd.gif        /// </summary>

419InBlock.gif        public bool AbortTask() 
420ExpandedSubBlockStart.gifContractedSubBlock.gif        dot.gif
421InBlock.gif            bool result = false;
422InBlock.gif            lockthis ) 
423ExpandedSubBlockStart.gifContractedSubBlock.gif            dot.gif
424InBlock.gif                if( _taskState == TaskStatus.Running && _workThread != null ) 
425ExpandedSubBlockStart.gifContractedSubBlock.gif                dot.gif
426InBlock.gif                    if (_workThread.ThreadState != System.Threading.ThreadState.Stopped)
427ExpandedSubBlockStart.gifContractedSubBlock.gif                    dot.gif{
428InBlock.gif                        _workThread.Abort();
429ExpandedSubBlockEnd.gif                    }

430InBlock.gif                    System.Threading.Thread.Sleep(2);
431InBlock.gif                    if (_workThread.ThreadState == System.Threading.ThreadState.Stopped)
432ExpandedSubBlockStart.gifContractedSubBlock.gif                    dot.gif{
433InBlock.gif                        // 更新任务工作状态 
434InBlock.gif                        _taskState = TaskStatus.Aborted; 
435InBlock.gif                        result = true;
436ExpandedSubBlockEnd.gif                    }

437InBlock.gif                    else
438ExpandedSubBlockStart.gifContractedSubBlock.gif                    dot.gif{
439InBlock.gif                        // 更新任务工作状态 
440InBlock.gif                        _taskState = TaskStatus.AbortPending; 
441InBlock.gif                        result = false;
442ExpandedSubBlockEnd.gif                    }

443InBlock.gif                    // 触发任务工作状态变化事件
444InBlock.gif                    FireStatusChangedEvent( _taskState, _result); 
445ExpandedSubBlockEnd.gif                }
 
446ExpandedSubBlockEnd.gif            }
 
447InBlock.gif            return result;
448ExpandedSubBlockEnd.gif        }
 
449InBlock.gif
450ExpandedSubBlockStart.gifContractedSubBlock.gif        /**//// <summary>
451InBlock.gif        /// 工作方法完成后的回调方法
452InBlock.gif        /// 将检查是否出错,并获取、更新返回结果值
453InBlock.gif        /// </summary>
454ExpandedSubBlockEnd.gif        /// <param name="ar">异步调用信号对象</param>

455InBlock.gif        protected void EndWorkBack( IAsyncResult ar ) 
456ExpandedSubBlockStart.gifContractedSubBlock.gif        dot.gif
457InBlock.gif            bool error = false;
458InBlock.gif            bool abort = false;
459InBlock.gif            try                                                //检查是否错误
460ExpandedSubBlockStart.gifContractedSubBlock.gif            dot.gif{
461InBlock.gif                TaskDelegate del = (TaskDelegate)ar.AsyncState; 
462InBlock.gif                _result = del.EndInvoke( ar ); 
463ExpandedSubBlockEnd.gif            }

464InBlock.gif            catch(Exception e)                                //如果错误,则保存错误对象
465ExpandedSubBlockStart.gifContractedSubBlock.gif            dot.gif{
466InBlock.gif                error = true;
467InBlock.gif                _exception = e;
468InBlock.gif                if (e.GetType() == typeof(System.Threading.ThreadAbortException))
469ExpandedSubBlockStart.gifContractedSubBlock.gif                dot.gif{
470InBlock.gif                    abort = true;
471InBlock.gif                    FireAbortEvent(_progress,_exception);
472ExpandedSubBlockEnd.gif                }

473InBlock.gif                else
474ExpandedSubBlockStart.gifContractedSubBlock.gif                dot.gif{
475InBlock.gif                    FireThrowErrorEvent(_progress,_exception);
476ExpandedSubBlockEnd.gif                }

477ExpandedSubBlockEnd.gif            }

478InBlock.gif            lockthis ) 
479ExpandedSubBlockStart.gifContractedSubBlock.gif            dot.gif
480InBlock.gif                if (error)
481ExpandedSubBlockStart.gifContractedSubBlock.gif                dot.gif{
482InBlock.gif                    if ( abort)
483ExpandedSubBlockStart.gifContractedSubBlock.gif                    dot.gif{
484InBlock.gif                        _taskState = TaskStatus.Aborted;        //调用者强行中止
485ExpandedSubBlockEnd.gif                    }

486InBlock.gif                    else
487ExpandedSubBlockStart.gifContractedSubBlock.gif                    dot.gif{
488InBlock.gif                        _taskState = TaskStatus.ThrowErrorStoped;//出现错误而中止
489ExpandedSubBlockEnd.gif                    }

490ExpandedSubBlockEnd.gif                }
 
491InBlock.gif                else
492ExpandedSubBlockStart.gifContractedSubBlock.gif                dot.gif{    _taskState = TaskStatus.Stopped;}          //正常结束
493InBlock.gif                FireStatusChangedEvent( _taskState, _result);
494ExpandedSubBlockEnd.gif            }
 
495ExpandedSubBlockEnd.gif        }
 
496ExpandedSubBlockEnd.gif        #endregion

497InBlock.gif
498ExpandedSubBlockStart.gifContractedSubBlock.gif        工作方法的基础#region 工作方法的基础
499ExpandedSubBlockStart.gifContractedSubBlock.gif        /**//// <summary>
500InBlock.gif        /// 工作方法
501InBlock.gif        /// 在继承类中应重写(override)此方法,以实现具体的工作内容,注意以几点:
502InBlock.gif        /// 1.须在继承类是引用base.Work,在基类(base)的Work方法中,执行线程设为IsBackground=true,并保存工作线程对象
503InBlock.gif        /// 2.在继承类中,应及时更新_progress与_result对象,以使Progress和Result属性值正确
504InBlock.gif        /// 3.在执行过程中应检查_taskState,以使任务中被请求停止后(_taskState为TaskStatus.CancelPending),工作线程能最快终止.
505InBlock.gif        /// 4.如在继承类中新定义了事件,应在此方法中引用触发
506InBlock.gif        /// 5.工作线程状态不由工作方法管理,所以在工作方法中不应改变_taskState变量值
507InBlock.gif        /// 6.工作方法中应对args参数进行有效检查
508InBlock.gif        /// </summary>
509InBlock.gif        /// <param name="args">传入的参数数组</param>
510ExpandedSubBlockEnd.gif        /// <returns>返回null</returns>

511InBlock.gif        virtual public object Work(params  object[] args )
512ExpandedSubBlockStart.gifContractedSubBlock.gif        dot.gif{
513InBlock.gif            System.Threading.Thread.CurrentThread.IsBackground = true;
514InBlock.gif            _workThread = System.Threading.Thread.CurrentThread;
515InBlock.gif            _result = null;
516InBlock.gif            return null;
517ExpandedSubBlockEnd.gif        }

518InBlock.gif
519ExpandedSubBlockEnd.gif        #endregion

520ExpandedSubBlockEnd.gif    }

521ExpandedBlockEnd.gif}

522 None.gif
523 ExpandedBlockStart.gifContractedBlock.gif 使用Task类 #region 使用Task类
524ExpandedSubBlockStart.gifContractedSubBlock.gif/**//*
525InBlock.gif
526InBlock.gif使用 Task 类
527InBlock.gif
528InBlock.gif一.在UI线程中创建Task类
529InBlock.gif
530InBlock.gifTask 类负责管理后台线程。要使用 Task 类,必须做的事情就是创建一个 Task 对象,注册它激发的事件,并且实现这些事件的处理。因为事件是在 UI 线程上激发的,所以您根本不必担心代码中的线程处理问题。
531InBlock.gif
532InBlock.gif下面的示例展示了如何创建 Task 对象。现假设UI 有两个按钮,一个用于启动运算,一个用于停止运算,还有一个进度栏显示当前的计算进度。
533InBlock.gif
534InBlock.gif// 创建任务管理对象
535InBlock.gif_Task = new Task(); 
536InBlock.gif// 挂接任务管理对象工作状态变化事件
537InBlock.gif_Task.TaskStatusChanged += new TaskEventHandler( OnTaskStatusChanged ); 
538InBlock.gif// 挂接任务管理对象工作进度变化事件
539InBlock.gif_Task.TaskProgressChanged += new TaskEventHandler( OnTaskProgressChanged ); 
540InBlock.gif
541InBlock.gif(1)
542InBlock.gif用于计算状态和计算进度事件的事件处理程序相应地更新 UI,例如通过更新状态栏控件。 
543InBlock.gif
544InBlock.gifprivate void OnTaskProgressChanged( object sender,TaskEventArgs e ) 
545InBlock.gif
546InBlock.gif    _progressBar.Value = e.Progress; 
547InBlock.gif
548InBlock.gif(2)
549InBlock.gif下面的代码展示的 TaskStatusChanged 事件处理程序更新进度栏的值以反映当前的计算进度。假定进度栏的最小值和最大值已经初始化。
550InBlock.gif
551InBlock.gifprivate void OnTaskStatusChanged( object sender, TaskEventArgs e ) 
552InBlock.gif
553InBlock.gif    switch ( e.Status ) 
554InBlock.gif    { 
555InBlock.gif        case TaskStatus.Running: 
556InBlock.gif            button1.Enabled = false; 
557InBlock.gif            button2.Enabled = true; 
558InBlock.gif            break; 
559InBlock.gif        case TaskStatus.Stop: 
560InBlock.gif            button1.Enabled = true; 
561InBlock.gif            button2.Enabled = false; 
562InBlock.gif            break; 
563InBlock.gif        case TaskStatus.CancelPending: 
564InBlock.gif            button1.Enabled = false; 
565InBlock.gif            button2.Enabled = false; 
566InBlock.gif            break; 
567InBlock.gif    } 
568InBlock.gif
569InBlock.gif
570InBlock.gif在这个示例中,TaskStatusChanged 事件处理程序根据计算状态启用和禁用启动和停止按钮。这可以防止用户尝试启动一个已经在进行的计算,并且向用户提供有关计算状态的反馈。
571InBlock.gif
572InBlock.gif通过使用 Task 对象中的公共方法,UI 为每个按钮单击实现了窗体事件处理程序,以便启动和停止计算。例如,启动按钮事件处理程序调用 StartTask 方法,如下所示。
573InBlock.gif
574InBlock.gifprivate void startButton_Click( object sender, System.EventArgs e ) 
575InBlock.gif
576InBlock.gif    _Task.StartTask( new object[] {} ); 
577InBlock.gif
578InBlock.gif
579InBlock.gif类似地,停止计算按钮通过调用 StopTask 方法来停止计算,如下所示。
580InBlock.gif
581InBlock.gifprivate void stopButton_Click( object sender, System.EventArgs e ) 
582InBlock.gif
583InBlock.gif    _Task.StopTask(); 
584InBlock.gif
585InBlock.gif
586InBlock.gif二.可能在非UI线程中使用Task类时
587InBlock.gif(1)和(2)应作如下改变
588InBlock.gif
589InBlock.gif(1)
590InBlock.gif用于计算状态和计算进度事件的事件处理程序相应地更新 UI,例如通过更新状态栏控件。 
591InBlock.gif
592InBlock.gifprivate void OnTaskProgressChanged( object sender,TaskEventArgs e ) 
593InBlock.gif
594InBlock.gif    if (InvokeRequired )        //不在UI线程上,异步调用
595InBlock.gif    {
596InBlock.gif        TaskEventHandler TPChanged = new TaskEventHandler( OnTaskProgressChanged ); 
597InBlock.gif        this.BeginInvoke(TPChanged,new object[] {sender,e});
598InBlock.gif    }
599InBlock.gif    else                        //更新
600InBlock.gif    {
601InBlock.gif        _progressBar.Value = e.Progress; 
602InBlock.gif    }
603InBlock.gif
604InBlock.gif(2)
605InBlock.gif下面的代码展示的 TaskStatusChanged 事件处理程序更新进度栏的值以反映当前的计算进度。假定进度栏的最小值和最大值已经初始化。
606InBlock.gif
607InBlock.gifprivate void OnTaskStatusChanged( object sender, TaskEventArgs e ) 
608InBlock.gif
609InBlock.gif    if (InvokeRequired )        //不在UI线程上,异步调用
610InBlock.gif    {
611InBlock.gif        TaskEventHandler TSChanged = new TaskEventHandler( OnTaskStatusChanged ); 
612InBlock.gif        this.BeginInvoke(TSChanged,new object[] {sender,e});
613InBlock.gif    }
614InBlock.gif    else                        //更新
615InBlock.gif    {
616InBlock.gif        switch ( e.Status ) 
617InBlock.gif        { 
618InBlock.gif            case TaskStatus.Running: 
619InBlock.gif                button1.Enabled = false; 
620InBlock.gif                button2.Enabled = true; 
621InBlock.gif                break; 
622InBlock.gif            case TaskStatus.Stop: 
623InBlock.gif                button1.Enabled = true; 
624InBlock.gif                button2.Enabled = false; 
625InBlock.gif                break; 
626InBlock.gif            case TaskStatus.CancelPending: 
627InBlock.gif                button1.Enabled = false; 
628InBlock.gif                button2.Enabled = false; 
629InBlock.gif                break; 
630InBlock.gif        } 
631InBlock.gif    }
632InBlock.gif
633InBlock.gif
634ExpandedSubBlockEnd.gif*/

635ExpandedBlockEnd.gif#endregion

636 None.gif



三、示例
1.启动时的UI界面
o_1.JPG

2.后台工作方法(费用方法)运行后,任务状态为Running
o_2.JPG

3.强制中止工作方法,运行任务状态Aborted
o_3.JPG

4.工作方法突发错误时,任务状态ThrowErrorStoped
o_4.JPG

5.工作方法正常结束或正常取消而结束时,任务状态Stopped
o_5.JPG

示例代码下载

转载于:https://www.cnblogs.com/net66/archive/2005/08/03/206132.html

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值