先在控制台中测试异步调用
首先声明一个具有int 和 out int 参数的委托AsyncDelegate,返回值为string
再声明一个threadId用来显示线程的ID
public
delegate
string
AsyncDelegate(
int
callDuration,
out
int
threadId);
private static int threadId;
private static int threadId;
在类AsyncDemo中建立异步方法
代码
public
string
TestMethod(
int
callDuration,
out
int
threadId)
{
Console.WriteLine( " 异步方法开始执行 " );
for ( int i = 0 ; i < 7 ; i ++ )
{
Thread.Sleep(callDuration);
Console.WriteLine( " 异步方法 " + i);
}
threadId = Thread.CurrentThread.ManagedThreadId;
Console.WriteLine(threadId);
Console.WriteLine( " 异步结束 " );
return " MyCallTime was " + callDuration.ToString();
}
{
Console.WriteLine( " 异步方法开始执行 " );
for ( int i = 0 ; i < 7 ; i ++ )
{
Thread.Sleep(callDuration);
Console.WriteLine( " 异步方法 " + i);
}
threadId = Thread.CurrentThread.ManagedThreadId;
Console.WriteLine(threadId);
Console.WriteLine( " 异步结束 " );
return " MyCallTime was " + callDuration.ToString();
}
异步方法在控制台上打印for循环,并且在for循环结束时打印当前线程的ID,最后返回string类型字符串。
在Main方法中创建一个测试类的实例,接着创建异步委托,然后使用BeginInvoke方法启动异步调用。其中包括两个异步委托的参数、一个AsyncCallback委托的回调方法还有一个object类型的参数(dlgt)。在异步委托中加入了异步所要调用的方法。
代码
static
void
Main(
string
[] args)
{
// 创建一个测试类的实例
AsyncDemo ad = new AsyncDemo();
// 创建委托
AsyncDelegate dlgt = new AsyncDelegate(ad.TestMethod);
// 启动异步调用. 包括一个 AsyncCallback委托的回调方法,
// 并且需要调用EndInvoke方法
// 前两个参数为异步方法的参数
IAsyncResult ar = dlgt.BeginInvoke( 1000 ,
out threadId,
new AsyncCallback(CallbackMethod),
dlgt);
//① dlgt.EndInvoke(out threadId, ar); 将优先执行异步方法在执行主方法
Console.WriteLine( " 主方法所在线程 " + Thread.CurrentThread.ManagedThreadId);
for ( int i = 0 ; i < 4 ; i ++ )
{
Thread.Sleep( 1000 );
Console.WriteLine( " 主线程 " + i);
}
Console.WriteLine( " 主方法结束 " );
//② dlgt.EndInvoke(out threadId, ar); 在此处添加没有效果
Console.ReadLine();
}
{
// 创建一个测试类的实例
AsyncDemo ad = new AsyncDemo();
// 创建委托
AsyncDelegate dlgt = new AsyncDelegate(ad.TestMethod);
// 启动异步调用. 包括一个 AsyncCallback委托的回调方法,
// 并且需要调用EndInvoke方法
// 前两个参数为异步方法的参数
IAsyncResult ar = dlgt.BeginInvoke( 1000 ,
out threadId,
new AsyncCallback(CallbackMethod),
dlgt);
//① dlgt.EndInvoke(out threadId, ar); 将优先执行异步方法在执行主方法
Console.WriteLine( " 主方法所在线程 " + Thread.CurrentThread.ManagedThreadId);
for ( int i = 0 ; i < 4 ; i ++ )
{
Thread.Sleep( 1000 );
Console.WriteLine( " 主线程 " + i);
}
Console.WriteLine( " 主方法结束 " );
//② dlgt.EndInvoke(out threadId, ar); 在此处添加没有效果
Console.ReadLine();
}
其中在①处如果使用EndInvoke方法,主线程将被阻塞,直到异步调用完成在继续执行主线程的打印。如果在②处使用则与没有加是同样的效果。
由此可见,当异步开始时主线程将按照顺序运行下去,一直遇到EndInvoke将主线程阻塞为止。
回调方法
代码
static
void
CallbackMethod(IAsyncResult ar)
{
// 取回委托.
AsyncDelegate dlgt = (AsyncDelegate)ar.AsyncState;
// 调用EndInvoke取回结果.
string ret = dlgt.EndInvoke( out threadId, ar);
// string ret = ar.ToString();
Console.WriteLine( " 调用在线程{0}上执行, 返回值 \ " { 1 }\ " . " , threadId, ret);
}
{
// 取回委托.
AsyncDelegate dlgt = (AsyncDelegate)ar.AsyncState;
// 调用EndInvoke取回结果.
string ret = dlgt.EndInvoke( out threadId, ar);
// string ret = ar.ToString();
Console.WriteLine( " 调用在线程{0}上执行, 返回值 \ " { 1 }\ " . " , threadId, ret);
}
回调方法是在异步方法结束时调用的,可以用来处理一些后续的操作。此处是打印回调方法所在的线程ID以及异步方法的返回值。
运行结果: