青青树官网:异步调用

来源:百度文库 编辑:九乡新闻网 时间:2024/04/29 20:54:26

异步调用

sulong 于 2010-06-29收藏说两句 ?

1 什么是异步

异步显然是和同步相对应的。同步调用,被调用者要执行完所有的代码才将执行流程交给调用者,在被调用者执行的过程中,调用者只能被动的等待;而异步,则是被调用先将执行流程转给调用者,然后自己再继续执行。如果调用者必须在得到被调用者的所有执行结果才能确定下一步该做什么的话,那么这种情况就该使用同步调用;相反,如果调用者不需要被调用者的执行结果,那么就可以使用异步。

2 怎样异步

在单线程或单进程等单一执行流程的情况下,实现不了能让被调用者个调用者并发执行的异步调用,这种情况下被调用者只能先将要执行的任务环境记录下来,带调用者执行完成后,再回头来执行之前要执行的任务,这样的方式其实算不上是异步,称之为推迟执行更贴切。

在多线程或多进程环境里,才能真正的实现异步,实现调用者和被调用者并发执行的异步调用。被调用者只要开启一个新的线程在新线程里执行任务,而立刻返回让调用者在当前线程继续执行,这样就可以实现异步调用了。

借助于ejb 3.1 , spring 3, seam这样的容器和框架,实现异步调用的方法非常简单,只需要再方法上加上指定的Annotation就可以了。使用spring 2的时候,可以注入taskExecutor,用taskExecutor.execute(Runnable r) 方法来实现异步。另外,通过JMS也可以实现异步。

3 异步有什么好处

说异步比同步调用性能好并不准确。假设 被调用方法里面要完成两个任务,分别耗时 t1和t2,从开始调用到调用返回的耗时,即响应时间,同步调用的时候,Rs = t1 + t2,异步调用的时候Ra = t1 + a1,其中a1代表为了异步调用开启新线程或新进程的耗时,如果要Ra < Rs,显然要求a1 < t2,可见如果异步执行的任务并不比启用异步执行耗时太多的话,异步执行也不会缩短响应时间。如果计算完成同等任务的总耗时的话,同步的时候 Ts = t1 + t2,异步的时候 Ta = t1 + a1 + t2,可见Ts < Ta,此时异步没有任何好处。在要求响应时间非常短的互联网应用中,合理的采用异步可以提高响应速度,提升程序的负载能力。快速的响应用户的请求,将耗时多而用户不急于知道结果的任务交给有限的线程来执行。

然而,对于Java EE这样的环境,一个事务的边界往往是在一个线程里的,所以使用异步之后,就失去了事务的保护,异常后的数据补偿工作增加了程序的复杂性,也让程序更容易出错。一个不好的异步实现机制,往往给程序带来更多的隐患。比如,为每一个异步执行的任务都新建一个线程,很可能在并发数到一定程度的时候,由于创建过多的线程,达到性能瓶颈,甚至于导致程序崩溃。

4 什么时候用异步

首先只有调用者不需要立刻知道结果的任务才能被异步执行;其次被异步执行的任务耗时多于使用异步执行本身的时候,采用异步才值得;再次,要求响应时间短的时候采用异步才有意义。

典型的例子:用户支付订单后要立刻告知用户支付是否成功,并给用户发送邮件,通知仓库发货,告知物流送货。这种情况下,用户只要知道支付成功就行了,发送邮件等任务用户可以过会再感知到,而且发送邮件等任务很耗时,用户肯定不愿意等待完成所有一切之后才知道支付结果。这种情况下,将发送邮件等任务异步执行就很合适。

另外一个例子,A,B两个系统每隔一个小时对一次账,如果B发现账户和A系统不一样,则自动调整。尽管A不需要知道B的调整结果,但是A完全可以等待B执行,反正也没人等也没人急,而且对账频率低负载低,这种情况下就没有必要异步执行调整动作。

相关文章:

  1. 企业应用集成–java与php
  2. 企业应用集成–java
  3. 漫谈PHP和Java
  4. JavaEE组件的并发与无状态
  5. 不读不是好程序员
 (No Ratings Yet)