您的位置:首页 > 其它

[转]Remoting之同步—异步调用

2007-08-16 08:57 591 查看
原文地址:http://challengerking.cnblogs.com/articles/364997.html

一. 前言

关于Remoting程序的调用效率问题,在刚做完项目中并未作为考虑因素加以考虑,无意中看到一篇关于Remoting的同步/异步调用方式的讨论的引论,于是打算对这个问题作一些解读,并通过程序来证明异步调用在提高Remoting效率方面的作用。

二. 简介

.NET Framework提供了三种调用远程对象的方法(不论是Server activated object, 或者是Client activated object), 你可以通过同步调用,异步调用,或者异步[OneWay]的方式来调用远程对象。

同步调用是一种基本的调用方式,在《Remoting随想》中涉及的所有的调用方式都是同步调用方式,客户端调用远程服务器端的方法如同调用本地方法一样。当服务器端接到客户端的调用请求后开始运行被调用的方法,而客户端必须的等待服务器端的方法执行完毕方可再发出请求。如果在远程方法调用过程中出现异常,则在你所调用的服务器端抛出异常。

异步调用分为两个步骤,第一个步骤是触发远程方法执行,而不必等待远程方法的返回值。客户端程序继续向下执行。当客户端收到被调用方法回复(response)后,这时须调用另一个专门用于检查服务器端是否已经执行完成了对客户端请求的业务;如果没有完成,则客户端等待,直到服务器端程序完成。在此过程中如果有异常发生,异常将会在被调用方法中出错的位置被抛出,即使你事先未被告知服务器端已在脱机状态下。

最后一种调用方式与前一种调用方式稍有不同,在[OneWay]调用方式下,若服务器端出现问题(如脱机,或者被调用方法未能完成业务功能),客户端程序(即调用方)将得不到返回值、异常原因。.NET Framework将试图在远端服务器端调用这个方法。

三.同步调用

前面已经提及,同步调用是.NET Framework的调用方法的通常方式。服务器端和被客户端直接通信,客户端程序将被阻塞,直到服务器端的方法运行完毕。如果服务器端不可用或者异常出现而无法满足客户段的需求,异常将会被抛出。

具体的各种Remoting部署方案可以参考我所写的《Remoting随想》那篇文章,采取任何一种类型都不会影响本文的讨论。这里我们列举一种是用接口的方式来说明同步/异步调用调用。接口的使用可以用关键字interface来定义一个接口,同样也可以用抽象类来实现。

3.1 接口定义

我们新建一个Class library工程,并在随后的服务器端和客户端添加对此DLL的引用。下面代码就是被引用DLL所需的接口定义。

定义RecordingManager.dll:


using System;
using System.Runtime.Remoting.Messaging;
namespace RecordingManager

3.2 同步调用模式下的服务器端程序

新建一个控制台程序,在服务器端来实现接口定义的方法,这个实现接口的类可以与服务器端主程序写在一起,也可以单独写成一个类,我们这里单独写为一个类,这样逻辑更佳清楚。

using System;
using System.Data;
using System.Data.OracleClient;
using System.Runtime.Remoting;
using RecordingManager;
using System.Runtime.Remoting.Messaging;
using System.Collections;
namespace TcpServer



using System;
using System.Runtime.Remoting;
using System.Runtime.Remoting.Channels;
using System.Runtime.Remoting.Channels.Tcp;
using RecordingManager;
using System.Data.OracleClient;
using System.Data;
using System.Runtime.Remoting.Messaging;
using System.Collections;
namespace TcpServer

3.3 同步调用模式下的客户端程序

新建一个控制台程序,调用服务器端方法。

using System;
using System.Runtime.Remoting;
using System.Runtime.Remoting.Channels.Tcp;
using System.Runtime.Remoting.Channels.Http;
using System.Runtime.Remoting.Channels;
using System.Runtime.Remoting.Proxies;
using System.Data;
using System.Data.OracleClient;
using RecordingManager;

namespace synchronizeTest
using System;
using System.Runtime.Remoting;
using System.Runtime.Remoting.Channels.Tcp;
using System.Runtime.Remoting.Channels.Http;
using System.Runtime.Remoting.Channels;
using System.Runtime.Remoting.Proxies;
using System.Data;
using System.Data.OracleClient;
using Recording;

namespace asynchronousClient

编译程序,先启动服务器端程序,在启动客户段程序,我们可以看到如图所示的结果,客户端调用两个方法用了2秒钟的时间(Fig 4-1),我们注意观察服务器端程序控制台所示(Fig 4-2),服务器端的两个程序是同时被调用的,这证明服务器端程序当第一个方法被调用执行的同时,第二个方法也开始执行,这样就完成了异步调用。

public abstract class BaseRemoteObject : MarshalByRefObject

注意:请始终牢记使用了异步One-Way调用方式时,客户端将忽视服务器端的返回值,并且不会去检查服务器端的运行状态。

六.小结

综合上述观点我们知道,的确,通过异步调用远程对象可以提高程序运行的效率,降低了由于某个方法的错误而造成整个应用程序崩溃的风险。
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: