.NET DELEGATES: A C # BedTime Story Chinese version (Part 2)
Author: Chris Sells
Translator: glory
[Translation] C # advanced article. Chris Sells is one of the author of "ATL INTERNALS". All program debugging environments in the translation are Microsoft Visual Studio.NET 7.0 Beta2 and Microsoft .NET Framework SDK Beta2. The code is the article, please read the code carefully J]
Get all results
Now, Peter finally loosked a breath. He has tried to meet all listeners and will not be closely coupled with specific implementation. However, he noted that although BOSS and Universe were scored for work, he only got a score. [Translation: Please refer to the previous example code and the translation] He hopes to get the results of each listener. Therefore, he decided to extract a list of commissioned calls for manual calls:
Public void doork ()
{
// ...
Console.writeline ("Worker: Work Completed");
IF (Completed! = NULL)
{
Foreach (Workcompleted WC In Completed.GetInvocationList ())
{
INT grade = WC ();
Console.writeline ("Worker grade =" grade);
}
}
}
[Translation: The following is an example of the complete code description of this section:
Using system;
Delegate void workstarted ();
Delegate void Workprogressing ();
Delegate int Workcompleted ();
Class worker
{
Public void doork ()
{
Console.writeline ("Worker: Work Started");
IF (Started! = null) Started ();
Console.writeline ("Worker: Work Progressing");
IF (Progressing! = NULL) progressing ();
Console.writeline ("Worker: Work Completed");
IF (Completed! = NULL)
{
Foreach (Workcompleted WC In Completed.GetInvocationList ())
{
INT grade = WC ();
Console.writeline ("Worker grade =" grade);
}
}
}
Public Event Workstarted Started;
Public Event WorkProgressing Progressing;
Public Event Workcompleted Completed;
}
Class boss
{
Public int Workcompleted ()
{
Console.writeline ("Better ...");
Return 4; / * Out of 10 * /
}
}
Class universe
{
Static void workerStartedWork ()
{
Console.Writeline ("Universe Notices Worker Starting Work");
}
Static int workercompletedwork () {
Console.writeline ("Universe PleaseD with Worker's Work");
Return 7;
}
Static void main ()
{
Worker peter = new worker ();
Boss boss = new boss ();
Peter.comPleted = New Workcompleted (Boss.WorkComplete);
Peter.Started = New Workstarted (universe.workerstartedWork);
Peter.comPleted = New Workcompleted (Universe.WorkerCompletedWork);
Peter.dowork ();
Console.writeline ("Main: worker completed work";
Console.readline ();
}
}
/ *
The following is the result of the upper program output:
Worker: Work Started
Universe Notices Worker Starting Work
Worker: Work Progressing
Worker: Work Completed
Better ...
Worker grade = 4 [Translation] 4 points of BOSS played J]
Universe pleased with worrs work
Worker grade = 7
Main: worker completed work
* /
】
Asynchronous notice: trigger and ignore
Unexpectedly, BOSS and Universe are eligible for anything else, which means that they are scored for Peter:
Class boss
{
Public int Workcompleted ()
{
System.threading.Thread.sleep (3000);
Console.writeline ("Better ...");
Return 6; / * Out of 10 * /
}
}
Class universe
{
Static int workercompletedWork ()
{
System.threading.Thread.sleep (4000);
Console.writeline ("Universe Is Plerated with Worker's Work");
Return 7;
}
// ...
}
Unfortunately, because Peter is informing BOSS and Universe and waiting for them to score, these returns now to occupy him a lot of working hours, so Peter decided to ignore rating and asynchronously trigger events:
Public void doork ()
{
// ...
Console.writeline ("Worker: Work Completed");
IF (Completed! = NULL)
{
Foreach (Workcompleted WC In Completed.GetInvocationList ())
{
Wc.BeginInvoke (NULL, NULL);
}
}
}
[Translation: The following example complete code is given below:
Using system;
Delegate void workstarted ();
Delegate void Workprogressing ();
Delegate int Workcompleted ();
Class worker {
Public void doork ()
{
Console.writeline ("Worker: Work Started");
IF (Started! = null) Started ();
Console.writeline ("Worker: Work Progressing");
IF (Progressing! = NULL) progressing ();
Console.writeline ("Worker: Work Completed");
IF (Completed! = NULL)
{
Foreach (Workcompleted WC In Completed.GetInvocationList ())
{
Wc.BeginInvoke (NULL, NULL);
}
}
}
Public Event Workstarted Started;
Public Event WorkProgressing Progressing;
Public Event Workcompleted Completed;
}
Class boss
{
Public int Workcompleted ()
{
System.threading.Thread.sleep (3000);
Console.writeline ("Better ...");
Return 6; / * Out of 10 * /
}
}
Class universe
{
Static void workerStartedWork ()
{
Console.Writeline ("Universe Notices Worker Starting Work");
}
Static int workercompletedWork ()
{
System.threading.Thread.sleep (4000);
Console.writeline ("Universe Is Plerated with Worker's Work");
Return 7;
}
Static void main ()
{
Worker peter = new worker ();
Boss boss = new boss ();
Peter.comPleted = New Workcompleted (Boss.WorkComplete);
Peter.Started = New Workstarted (universe.workerstartedWork);
Peter.comPleted = New Workcompleted (Universe.WorkerCompletedWork);
Peter.dowork ();
Console.writeline ("Main: worker completed work";
Console.readline ();
}
}
/ *
The following is the result of the upper program output:
Worker: Work Started
Universe Notices Worker Starting Work
Worker: Work Progressing
Worker: Work Completed
Main: worker completed work // 【Translation: Because it is an asynchronous trigger event, this line is output first.
Better ... // [Translation: The score has been ignored]
Universe pleased with worker's work //: rating has been ignored]
* /
】
Asynchronous notice: polling
This allows Peter to notify the listener while you can return to work immediately, let the process's thread pool call. Soon, he found that the listener lost the score of his work. [Translation: Please refer to the previous example code and the translation] Peter knows that he did a sensible thing and would like to judge him as a whole (not only his boss). Therefore, Peter triggers event, but regular polls to check the score available: public void Dowork ()
{
// ...
Console.writeline ("Worker: Work Completed");
IF (Completed! = NULL)
{
Foreach (Workcompleted WC In Completed.GetInvocationList ())
{
IASYNCRESULT RES = Wc.BeginInvoke (NULL, NULL);
While (! res.iscompleted) system.threading.thread.sleep (1);
INT grade = wc.endinvoke (res);
Console.writeline ("Worker grade =" grade);
}
}
}
[Translation: The following example complete code is given below:
Using system;
Delegate void workstarted ();
Delegate void Workprogressing ();
Delegate int Workcompleted ();
Class worker
{
Public void doork ()
{
Console.writeline ("Worker: Work Started");
IF (Started! = null) Started ();
Console.writeline ("Worker: Work Progressing");
IF (Progressing! = NULL) progressing ();
Console.writeline ("Worker: Work Completed");
IF (Completed! = NULL)
{
Foreach (Workcompleted WC In Completed.GetInvocationList ())
{
IASYNCRESULT RES = Wc.BeginInvoke (NULL, NULL);
While (! res.iscompleted) system.threading.thread.sleep (1);
INT grade = wc.endinvoke (res);
Console.writeline ("Worker grade =" grade);
}
}
}
Public Event Workstarted Started;
Public Event WorkProgressing Progressing;
Public Event Workcompleted Completed;
}
Class boss
{
Public int Workcompleted ()
{
System.threading.Thread.sleep (3000);
Console.writeline ("Better ...");
Return 6; / * Out of 10 * /
}
}
Class universe
{
Static void workerStartedWork ()
{
Console.writeline ("Universe Notices Worker Starting Work");
Static int workercompletedWork ()
{
System.threading.Thread.sleep (4000);
Console.writeline ("Universe Is Plerated with Worker's Work");
Return 7;
}
Static void main ()
{
Worker peter = new worker ();
Boss boss = new boss ();
Peter.comPleted = New Workcompleted (Boss.WorkComplete);
Peter.Started = New Workstarted (universe.workerstartedWork);
Peter.comPleted = New Workcompleted (Universe.WorkerCompletedWork);
Peter.dowork ();
Console.writeline ("Main: worker completed work";
Console.readline ();
}
}
/ *
The following is the result of the upper program output:
Worker: Work Started
Universe Notices Worker Starting Work
Worker: Work Progressing
Worker: Work Completed
Better ...
Worker grade = 6
Universe pleased with worrs work
Worker grade = 7
Main: worker completed work // [Mode note: Pay attention to this result to finally output, the first sentence is the case]
* /
】
Asynchronous notice: commission
Unfortunately, Peter returned - just like he wanted to avoid BOSS to stand aside him. That is, he must monitor the entire work process now. [Translation: Please refer to the result of the previous example output] Therefore, Peter decided to use his delegate as a notification method when the asynchronous entrusted is complete, so that he can go back to work immediately, and when the work is scored, it can still be notified :
Public void doork ()
{
// ...
Console.writeline ("Worker: Work Completed");
IF (Completed! = NULL)
{
Foreach (Workcompleted WC In Completed.GetInvocationList ())
{
Wc.BeginInvoke (New AsyncCallback (Workgraded), WC);
}
}
}
Private void Workgraded (IasyncResult RES)
{
Workcompleted WC = (Workcompleted) res. degasncstate;
INT grade = wc.endinvoke (res);
Console.writeline ("Worker grade =" grade);
}
[Translation: The following example complete code is given below:
Using system;
Delegate void workstarted ();
Delegate void Workprogressing ();
Delegate int Workcompleted (); Class Worker
{
Public void doork ()
{
Console.writeline ("Worker: Work Started");
IF (Started! = null) Started ();
Console.writeline ("Worker: Work Progressing");
IF (Progressing! = NULL) progressing ();
Console.writeline ("Worker: Work Completed");
IF (Completed! = NULL)
{
Foreach (Workcompleted WC In Completed.GetInvocationList ())
{
Wc.BeginInvoke (New AsyncCallback (Workgraded), WC);
}
}
}
Private void Workgraded (IasyncResult RES)
{
Workcompleted WC = (Workcompleted) res. degasncstate;
INT grade = wc.endinvoke (res);
Console.writeline ("Worker grade =" grade);
}
Public Event Workstarted Started;
Public Event WorkProgressing Progressing;
Public Event Workcompleted Completed;
}
Class boss
{
Public int Workcompleted ()
{
System.threading.Thread.sleep (3000);
Console.writeline ("Better ...");
Return 6; / * Out of 10 * /
}
}
Class universe
{
Static void workerStartedWork ()
{
Console.Writeline ("Universe Notices Worker Starting Work");
}
Static int workercompletedWork ()
{
System.threading.Thread.sleep (4000);
Console.writeline ("Universe Is Plerated with Worker's Work");
Return 7;
}
Static void main ()
{
Worker peter = new worker ();
Boss boss = new boss ();
Peter.comPleted = New Workcompleted (Boss.WorkComplete);
Peter.Started = New Workstarted (universe.workerstartedWork);
Peter.comPleted = New Workcompleted (Universe.WorkerCompletedWork);
Peter.dowork ();
Console.writeline ("Main: worker completed work";
Console.readline ();
}
}
/ * The following is the result of the upper program output:
Worker: Work Started
Universe Notices Worker Starting Work
Worker: Work ProgressingWorker: Work Completed
Main: worker completed work // [Translation: Asynchronous entrusted effect, so this line is output first.
Better ...
Worker grade = 6
Universe pleased with worrs work
Worker grade = 7
* /
】
Tongle
Peter, BOSS and Universe are ultimately satisfied. Both BOSS and Universe can only notify the incidents of interest and reduce the burden on the implementation and unnecessary commencement. Peter can inform them that each person does not have to return from those objective methods, and can still be scored asynchronously. Peter knows this is not too easy because it is asynchronous triggering event, the target method is likely to run in another thread, as the previous example. However, Peter [J] and Mike [J] are good friends, while Mike is proficient in thread problems and provides guidance in this area.
Since then, they are very happy J
- Full text -