对于IO密集型操作来说,异步执行对于应用程序的响应能力和伸缩性有非常关键的影响。
对于大量的IO操作,异步执行方式使主线程不必等待服务器返回结果,继续执行后面的代码,大大地提高了效率。
Flash Player 是一个多线程的软件,但它不提供多线程的API。在我们看来,它是单线程的。
FLEX异步调用可通过二种方法:
1.添加事件监听器
FLEX的事件处理是异步的,不过通过事件监听器易代码比较混乱。
import mx.rpc.events.FaultEvent;
import mx.collections.ArrayCollection;
import mx.rpc.remoting.mxml.RemoteObject;
import mx.controls.Alert;
import mx.rpc.events.ResultEvent;
public function submit():void{
var remote:RemoteObject = new RemoteObject();
//调用在J2EE端remoting-config.xml中配置的暴露出的类的名称 id
remote.destination = "helloWorld";
//调用J2EE端类中的方法
remote.getHelloWorld();
//监听调用成功事件
remote.addEventListener(ResultEvent.RESULT,result);
//监听失败事件
remote.addEventListener(FaultEvent.FAULT,fault);
}
private function result(evt:ResultEvent):void{
Alert.show(evt.result.toString());
}
private function fault(evt:FaultEvent):void{
Alert.show("调用失败!");
}
]]>
说明
利用事件监听方法,XXX_resultHandler、faultHandler函数可以直接写在页面上,但这样增加了耦合性,比如在页面上直接写如下代码:
public function search(searchStr:String):void
{
lastSearchStr = searchStr;
service.getContactsByName(searchStr).addResponder(new AsyncResponder(getContacts_result, faultHandler));
}
private function getContacts_result(event:ResultEvent, token:AsyncToken):void
{
contacts = event.result as ArrayCollection;
}
private function faultHandler(event:FaultEvent):void
{
Alert.show(event.fault.faultString);
}
2.异步响应类AsyncResponder
异步调用必须实现IResponder接口,该
接口为任何需要响应远程或异步调用的服务提供协定。接口中饮食两个方法:
1.public function fault(info:Object):void
收到错误后由服务调用此方法。虽然 info 被分类为对象,但它通常是(但不总是)一个 mx.rpc.events.FaultEvent。
2.public function result(data:Object):void
收到返回值后由服务调用此方法。虽然 data 被分类为对象,但它通常是(但不总是)一个 mx.rpc.events.ResultEvent。
类AsyncResponder 实现了IResponder接口,并提供异步调用服务。该类只有三个方法
1.public function AsyncResponder(result:Function, fault:Function, token:Object = null)
使用指定的数据和处理函数构造 responder 实例。
参数
result:Function — 成功完成请求时应调用的函数。格式如下:
public function (result:Object, token:Object = null):void;
fault:Function — 请求完成但出错时应调用的函数。格式如下:
public function (error:FaultEvent, token:Object = null):void;
token:Object (default = null) — 与此请求相关的其他信息。
2.public function fault(info:Object):void
收到错误后由服务调用此方法。
参数
info:Object — 包含有关发生的错误的信息的对象。
3.public function result(data:Object):void
收到返回值后由服务调用此方法。
参数
data:Object — 包含从请求返回的信息的对象。
例子:
xmlns:s="library://ns.adobe.com/flex/spark"
xmlns:mx="library://ns.adobe.com/flex/mx"
xmlns:parsley=""
minWidth="955" minHeight="600">
import com.home.system.model.UserModel;
import com.home.system.services.mock.LoginServiceMock;
import com.home.utils.MockServiceUtil;
import mx.controls.Alert;
import mx.rpc.AsyncResponder;
import mx.rpc.AsyncToken;
import mx.rpc.events.FaultEvent;
import mx.rpc.events.ResultEvent;
[Bindable]
public var _username : String;
[Bindable]
public var _password : String;
//模拟远程对象
public var mockService:MockServiceUtil = new MockServiceUtil();
public function login () : AsyncToken {
var model1:UserModel;
model1 = new UserModel();
model1.xh="995312";
model1.xm="王一冰";
//添加一个异步桩,用于异步接收处理
var token:AsyncToken = mockService.createToken(model1);
token.addResponder(new AsyncResponder(login_resultHandler, faultHandler,model1));
return token;
}
private function login_resultHandler(event:ResultEvent,model:UserModel):void
{
var result :UserModel =event.result as UserModel;
Alert.show("event.result:"+result.xm);
Alert.show("UserModel:"+model.xh);
}
private function faultHandler(event:FaultEvent, token:Object = null):void
{
Alert.show(event.fault.faultString);
}
private function handleKeyUp(event:KeyboardEvent):void {
if( event.keyCode == Keyboard.ENTER ) {
login();
}
}
]]>
text="{_password}" displayAsPassword="true"/>
label="login"
click="login()"
keyUp="handleKeyUp(event)"
x="86" y="97"/>
注意:
token.addResponder(new AsyncResponder(login_resultHandler, faultHandler,model1));
也可以写成:
token.addResponder(new AsyncResponder(login_resultHandler, faultHandler));
这样的话,响应函数也得改成
private function login_resultHandler(event:ResultEvent):void
private function faultHandler(event:FaultEvent):void
参考文献
1. AsyncResponder类.
阅读(7411) | 评论(0) | 转发(0) |