77.html

来自「写给JSP初级程序员的书」· HTML 代码 · 共 265 行 · 第 1/2 页

HTML
265
字号
        Socket clientSocket =new Socket("serverName",7);&nbsp;<br> 
        OutputStream os=clientSocket.getOutputStream();&nbsp;<br> 
        DataInputStream is=new DataInputStream( clientSocket.getInputStream());&nbsp;<br> 
        // 其它操作.&nbsp;<br> 
        os.close();&nbsp;<br> 
        is.close();&nbsp;<br> 
        clientSocket.close();&nbsp;<br> 
        }catch(Exception e){&nbsp;<br> 
        System.err.println("Exception:"+e);&nbsp;<br> 
        }&nbsp;<br> 
        <br> 
                     这种方法只依赖于标准的Java网络支持,不需要用到附加的软件包或工具, 因此显得相当简洁和灵活,易于实现某些特殊的需要。但在另一方面,服务器端对进入请求以及客户端对返回结果的分析工作量较大。如果服务器端要执行大量的操作,可以考虑使用RMI。&nbsp;<br> 
        <br> 
                     三、远程方法调用RMI&nbsp;<br> 
        <br> 
                     Java的RMI技术显著地改善了客户程序操作复杂的服务器端对象的能力。对Applet来说,服务器端对象所提供的远程方法可以象普通的客户端句柄一样调用。使用RMI时应先定义远程接口,即一个继承自java.rmi.Remote的公用接口。在该接口中定义要求在服务器上运行的方法,所有这些方法的throws子句至少应该声明java.rmi.RemoteException异常。&nbsp;<br> 
        <br> 
                     接下来是实现远程接口,远程接口的实现类应该:&nbsp;<br> 
        <br> 
                     ⑴ 指定所实现的一个或多个接口。&nbsp;<br> 
        <br> 
                     ⑵ 定义远程对象的构造方法。&nbsp;<br> 
        <br> 
                     ⑶ 提供所有可供远程调用的方法的实现。&nbsp;<br> 
        <br> 
                     ⑷ 创建和安装安全管理器。&nbsp;<br> 
        <br> 
                     ⑸ 创建一个或多个远程对象实例。&nbsp;<br> 
        <br> 
                     ⑹ 注册至少一个远程对象。&nbsp;<br> 
        <br> 
                     下面的代码实现一个返回日期字符串的getData()远程方法,该方法由接口RMIServ2App定义:&nbsp;<br> 
        // 本类继承自UnicastRemoteObject,实现接口serv2app&nbsp;<br> 
        <br> 
        package com.servletsolutions.serv2app.rmi;&nbsp;<br> 
        <br> 
        import java.rmi.*;&nbsp;<br> 
        import java.rmi.server.*;&nbsp;<br> 
        <br> 
        public class RMIImplementation extends UnicastRemoteObject&nbsp;<br> 
        implements RMIServ2App{&nbsp;<br> 
        public RMIImplementation() throws RemoteException{}&nbsp;<br> 
        public String getData() throws RemoteException{&nbsp;<br> 
        return java.text.DateFormat.getDateInstance().format(&nbsp;<br> 
        new java.util.Date());&nbsp;<br> 
        }&nbsp;<br> 
        <br> 
        public static void main(String[] args){&nbsp;<br> 
        // 安全管理器&nbsp;<br> 
        System.setSecurityManager(new RMISecurityManager());&nbsp;<br> 
        try{&nbsp;<br> 
        // 远程对象实例&nbsp;<br> 
        RMIImplementation bootStrap = new RMIImplementation();&nbsp;<br> 
        // 注册&nbsp;<br> 
        Naming.bind(args[0], bootStrap);&nbsp;<br> 
        System.out.println(args[0] + " 注册成功");&nbsp;<br> 
        }catch(Exception e){&nbsp;<br> 
        System.err.println("注册失败.");&nbsp;<br> 
        System.err.println(e);&nbsp;<br> 
        }&nbsp;<br> 
        }&nbsp;<br> 
        }&nbsp;<br> 
        <br> 
                     在客户端,Applet对接口RMIServ2App的引用通过调用Naming.lookup(String)获得,如下所示:&nbsp;<br> 
        <br> 
                     RMIServ2App obj = (RMIServ2App)Naming.lookup("//" + getCodeBase().getHost() + "/ServerName");&nbsp;<br> 
        <br> 
                     除了编译Java代码之外,还要用rmic编译器生成远程对象的存根和骨架。存根(Stub)是远程对象在客户端的代理,它将RMI调用传递给服务器端的骨架(Skeleton),后者负责将该调用传递给实际的远程方法。例如执行命令rmic com.servletsolutions.RMIImplementation,则生成的两个类文件分别为RMIImplementation_Stub.class 和RMIImplementation_Stub.class,前者封装入Applet且运行于客户端,后者封装入Servlet且运行与服务器端。&nbsp;<br> 
        <br> 
                     当大量的数据是由服务器端的对象动态提供时使用RMI是非常合适的。虽然RMI支持面向对象的分布式编程,但它要求客户端和服务器端都是Java程序。因此,对于使用混合语言开发的应用来说,CORBA比RMI更为适用。&nbsp;<br> 
        <br> 
                     四、使用CORBA&nbsp;<br> 
        <br> 
                     CORBA即公用对象请求代理体系(Common Object Request Broker Architecture),它的使用方法类似于RMI:定义接口,使用某个工具创建Stub和Skeleton,实现接口,在服务器上注册后客户就可以像本地对象一样访问远程对象了。两者主要的不同之处在于,CORBA使用一种语言中立的接口定义语言(IDL)来定义接口,IDL是一种可用于混合语言环境的更为广泛的协议集。CORBA最大的缺点在于客户本身必须具备调用ORB的能力,这往往意味着增加一个体积较大的JAR文件。&nbsp;<br> 
        <br> 
                     下面的CORBAServ2App.idl是上述getData()接口的IDL描述,它定义了一组与Java包名字对应的嵌套模块:&nbsp;<br> 
        module com {&nbsp;<br> 
        module servletsolutions {&nbsp;<br> 
        module serv2app {&nbsp;<br> 
        module corba {&nbsp;<br> 
        interface CORBAServ2App{&nbsp;<br> 
        string getData();&nbsp;<br> 
        };&nbsp;<br> 
        };&nbsp;<br> 
        };&nbsp;<br> 
        };&nbsp;<br> 
        };&nbsp;<br> 
        <br> 
                     可以用idl2java从IDL文件生成对应的java文件。其中_CORBAServ2AppImplBase.java包含了描述该接口的java抽象类,下面的CORBAImplementation类继承自抽象类_CORBAServ2AppImplBase并具体实现getData()方法:&nbsp;<br> 
        package com.servletsolutions.serv2app.corba;&nbsp;<br> 
        <br> 
        public class CORBAImplementation extends _CORBAServ2AppImplBase {&nbsp;<br> 
        CORBAImplementation(String s){ super(s); }&nbsp;<br> 
        public String getData(){&nbsp;<br> 
        return java.text.DateFormat.getDateInstance().format(new java.util.Date());&nbsp;<br> 
        }&nbsp;<br> 
        }&nbsp;<br> 
        <br> 
                     为了让该类可以被客户访问,Servlet中还应该创建其实例。代码如下所示:&nbsp;<br> 
        // 在Servlet的init()方法中初始化CORBAImplementation对象&nbsp;<br> 
        // 其中BOA(Basic Object Adapter)的作用类似于RMI中的注册服务&nbsp;<br> 
        <br> 
        public class CORBAServlet extends HttpServlet{&nbsp;<br> 
        String CORBAName;&nbsp;<br> 
        public void init(&nbsp;<br> 
        ServletConfig config) throws ServletException {&nbsp;<br> 
        super.init(config);&nbsp;<br> 
        try {&nbsp;<br> 
        CORBAName = getInitParameter("CORBAName");&nbsp;<br> 
        org.omg.CORBA.ORB orb = org.omg.CORBA.ORB.init();&nbsp;<br> 
        org.omg.CORBA.BOA boa = orb.BOA_init();&nbsp;<br> 
        com.servletsolutions.serv2app.corba.CORBAServ2App implObject =&nbsp;<br> 
        new CORBAImplementation(CORBAName);&nbsp;<br> 
        boa.obj_is_ready(implObject);&nbsp;<br> 
        boa.impl_is_ready();&nbsp;<br> 
        }&nbsp;<br> 
        catch (Exception e) {&nbsp;<br> 
        e.printStackTrace();&nbsp;<br> 
        }&nbsp;<br> 
        }&nbsp;<br> 
        <br> 
                     IDL2Java同时为客户端生成CORBAServ2AppHelper类,Applet通过该类与服务器交互。Stub与Skeletion的作用类似于它们在RMI中,不同之处在于本地ORB接口负责所有与远程ORB之间的连接。&nbsp;<br> 
        <br> 
                     如果服务器端的数据计算量非常大(比如数据库操作),或在未知客户端应用程序的情况下需要从服务器端引出大量的功能,RMI和CORBA较为合适。考虑到已有大量可用的ORB以及CORBA规范的成熟,在大多数情况下CORBA更为可取。但如果希望减小客户端的复杂程度,则RMI是最好的方法。<br>  
        </td>
      </tr>
    </td>
  </tr>
</div>
</body>
</html>

⌨️ 快捷键说明

复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?