隨筆-159  評(píng)論-114  文章-7  trackbacks-0
          簡(jiǎn)單來(lái)說(shuō),要實(shí)現(xiàn)A機(jī)器上JVM上運(yùn)行的Java程序,遠(yuǎn)程調(diào)用B機(jī)器上JVM上的Java程序,計(jì)算完畢,返回給A機(jī)器。

          在沒(méi)有RMI的情況下,我們使用普通的網(wǎng)絡(luò)傳輸技術(shù)能完成么?當(dāng)然,兩種選擇,Socket直接通訊,將參數(shù)傳給B,B在通過(guò)Socket返還給調(diào)用者。或者通過(guò)Servlet也可以遠(yuǎn)程調(diào)用阿。

          那么這樣解決問(wèn)題時(shí)沒(méi)有問(wèn)題,但對(duì)于A和B來(lái)說(shuō),代碼量、程序復(fù)用程序、維護(hù)性都不會(huì)太理想。

          如果能讓調(diào)用者不知道網(wǎng)絡(luò)操作,實(shí)現(xiàn)對(duì)于用戶(hù)透明,也就是像調(diào)用本地一樣,對(duì)象名.方法名。

          那么就是RMI規(guī)范涉及到一些接口。

          面向接口的編程方式,就可以達(dá)到代碼的實(shí)現(xiàn)與聲明分離。

          這樣用戶(hù)就只關(guān)心接口了。很多細(xì)節(jié)讓遵守規(guī)范(也就是一些編寫(xiě)好的工具)的實(shí)現(xiàn)類(lèi)去完成吧。[就是Stub和Skeleton]

          那么就先定一個(gè)用戶(hù)A要知道怎么用,B要知道方法簽名完成實(shí)現(xiàn),的同一接口吧。

          import?java.rmi.*;

          public?interface?Compute?extends?Remote{
          ????
          ????
          public?double?add(double?a,double?b)?throws?RemoteException;
          ????
          }

          兩點(diǎn)要求

          1,繼承標(biāo)記接口Remote。

          identify interfaces whose methods may be invoked from a non-local virtual machine.

          標(biāo)識(shí)該接口可以被非本地VM調(diào)用唄。

          2,里面每個(gè)方法都要拋出RemoteException


          業(yè)務(wù)接口的實(shí)現(xiàn)類(lèi),也就是做實(shí)事的類(lèi)

          import?java.rmi.server.*;
          import?java.rmi.*;

          public?class?ComputeImpl?extends?UnicastRemoteObject?implements?Compute
          {
          ????
          //要在構(gòu)造方法拋出異常
          ????public?ComputeImpl()?throws?RemoteException{}
          ????
          ????
          public?double?add(double?a,double?b){
          ????????
          return?a+b;
          ????}

          }


          =====================
          javac *.class

          rmic -keep ComputeImpl
          帶參數(shù),可以保留Stub和Skeleton源碼。

          通過(guò)ComputeImpl的實(shí)現(xiàn)類(lèi)來(lái)生成負(fù)責(zé)通訊的Stub(存根)和Skeleton(框架)

          ======================

          那么就是要把這個(gè)對(duì)象綁定到一個(gè)端口上。

          以便別人來(lái)使用

          編寫(xiě)一個(gè)Server

          import?java.rmi.*;

          public?class?Server
          {

          ????
          public?static?void?main(String[]?args)?throws?Exception
          ????
          {
          ????????ComputeImpl?c?
          =?new?ComputeImpl();
          ????????Naming.bind(
          "rmi://localhost:8888/compute",c);//compute別名
          ????}


          }

          客戶(hù)端

          import?java.rmi.*;

          public?class?Client
          {
          ????
          public?static?void?main(String[]?args)?throws?Exception
          ????
          {
          ????????Compute?c?
          =?(Compute)Naming.lookup("rmi://localhost:8888/compute");//rmiregistry首先響應(yīng)
          ????????
          //實(shí)際c是Stub對(duì)象
          ????????System.out.println(c.getClass());
          ????????System.out.println(c.add(
          12.3,34));
          ????}
          ???
          }


          ?看到?jīng)]有,客戶(hù)端通過(guò)rmi協(xié)議到服務(wù)器上尋找/compute資源對(duì)象。那個(gè)Naming是RMI專(zhuān)用,不是JNDI。

          那么Server類(lèi)并沒(méi)有負(fù)責(zé)監(jiān)聽(tīng)阿。

          哦,最后有一個(gè)強(qiáng)大的工具在JAVA_HOME/bin/下,叫做rmiregistry,專(zhuān)門(mén)負(fù)責(zé)監(jiān)聽(tīng)固定端口上,rmi協(xié)議的請(qǐng)求。

          =================
          rmiregistry 8888

          =================

          啟動(dòng)Server,綁定遠(yuǎn)程對(duì)象阿

          java Server

          =================

          啟動(dòng)一個(gè)Client,調(diào)用一下

          java Client

          =================

          rmi.jpg

          ===============

          另外一些小問(wèn)題

          由于rmiregistry 工具的不斷強(qiáng)大,jdk1.4已經(jīng)可以不再使用skeleton,到1.5,根本就不生成skeleton了。

          rmiregistry可以充當(dāng)skeleton角色完成功能。

          記住EJB中,還不行,因?yàn)闆](méi)有rmiregistry工具了。呵呵,明白了?

          =========================

          所以什么呢,RMI就是一種代理模式的應(yīng)用Stub,就是實(shí)際實(shí)現(xiàn)類(lèi)的客戶(hù)代理。

          但需要統(tǒng)一的接口,才能對(duì)于用戶(hù)、調(diào)用者透明??!

          ------------------------


          我說(shuō)的比較通俗。還有很多深刻的東西。

          posted on 2006-03-19 22:42 北國(guó)狼人的BloG 閱讀(1343) 評(píng)論(0)  編輯  收藏 所屬分類(lèi): 達(dá)內(nèi)學(xué)習(xí)總結(jié)
          主站蜘蛛池模板: 南丰县| 将乐县| 高青县| 长阳| 兴城市| 台州市| 江油市| 正蓝旗| 开阳县| 湟中县| 普安县| 江口县| 永顺县| 长沙市| 新建县| 霸州市| 临潭县| 乌苏市| 泸州市| 青阳县| 深泽县| 泾阳县| 裕民县| 宿州市| 五家渠市| 封开县| 潜山县| 静宁县| 邳州市| 通海县| 贡山| 佛山市| 山东| 洪洞县| 亚东县| 西贡区| 丹阳市| 闽清县| 调兵山市| 始兴县| 东安县|