2011-12-22 30 views
1

這是一個有關RMI的問題。我有4個.class文件接口,它是實現,一個名爲server的類和一個名爲client的類。該課程的內容如何打印,我還沒有開始CMD

開始rmiregistry中i之後開始這就好比服務器:

import java.rmi.Naming; 


public class Server { 
    public static void main(String args[]) { 
     try { 
      to_Server_Impl toServer = new to_Server_Impl(); 
      Naming.rebind("Server", toServer); 
     } catch(Exception exc) { 
      System.out.println(exc); 
     } 
    } 
} 

然後我啓動其代碼是客戶端:

import java.rmi.Naming; 
import java.io.BufferedReader; 
import java.io.InputStreamReader; 
import java.io.IOException; 


public class Client { 
    public static void main(String args[]) { 
     try { 
      to_Server_Intf s_Intf = (to_Server_Intf)Naming.lookup("rmi://127.0.0.1/Server"); 
      do { 
      BufferedReader br = new BufferedReader(new InputStreamReader(System.in)); 
      String message_to_send = null; 
      System.out.println("===Enter your message==="); 
      message_to_send = br.readLine(); 
      // sending a message to the server 
      String reply = s_Intf.send(message_to_send); 
      System.out.println(reply); 
      }while(true); 
     }catch(Exception exc) { 
      System.out.println(exc); 
     } 
    } 
} 

使用遙控對象的引用i調用函數send,其代碼如下:

import java.rmi.*; 
import java.rmi.server.*; 
import java.io.BufferedReader; 
import java.io.InputStreamReader; 
import java.io.IOException; 

public class to_Server_Impl extends UnicastRemoteObject implements to_Server_Intf{ 
    public to_Server_Impl() throws Exception{ } 

@Override 
public String send(String str){ // this function receives the message from the Client. 
    // this method indirectly replies,by calling reply and then returning the replies string 
    String receivedString = str;   
    System.out.println(receivedString); 
    System.out.println(); 
    String reply = reply(); 

    return reply; 
} 

@Override 
public String reply() { // this function replies the Client 
    String replyString = null; 
     try { 
      BufferedReader br = new BufferedReader(new InputStreamReader(System.in)); 
      replyString = br.readLine(); 
     }catch(Exception exc) { 
      System.out.println(exc); 
     } 
    return replyString; 
} 
} 

當我調用上述類的print語句的方法時,在「server」窗口中打印消息。這怎麼可能?

客戶端窗口:(客戶端發送的消息)

enter image description here

服務器窗口:(消息獲取打印服務器窗口上(呼叫被定向到類to_Server_Impl)的功能。怎麼樣?)

enter image description here

回答

2

我不明白你的問題。在send方法中(即在服務器上,即由服務器上的遠程客戶端調用它),您正在打印接收到的消息。因此,它出現在服務器控制檯中。

編輯:從本質上講,這是RMI是如何工作的:

服務器應用程序發佈與可用方法的接口調用。在你的情況下,這是to_Server_Intf。該服務器還具有該接口的實現,該接口是to_Server_Impl。服務器將Naming.bind(或Naming.rebind)的遠程對象發佈到註冊表。

客戶端只知道服務器上的接口,但不知道實現。他們可以在註冊表上執行查找,並按照名稱Naming.lookup查找遠程對象。現在客戶端有一個遠程對象實例,可以調用它的方法。該對象(客戶端代碼中的s_intf)實際上是服務器上存在的接口實現的本地代理。當客戶端在該代理上調用方法時,該調用實際上被髮送到服務器上的對象,這就是爲什麼您在服務器控制檯中看到該字符串的原因。

客戶端在本地存根上調用方法時發生的實際情況是參數(如果有)被序列化並創建一個TCP套接字消息(或任何底層實現),該消息被髮送給服務器正在監聽傳入的請求。在服務器端,收到消息,參數被反序列化,從消息中識別出正確的方法並進行調用。該方法返回後,再次將結果序列化,創建一條TCP消息發送回客戶端。

+0

我稱之爲類'to_Server_Impl'的send方法。它如何出現在「服務器」控制檯上? – 2011-12-22 11:25:55

+0

因爲to_Server_Impl是遠程對象的接口的實現。在客戶端中,您使用Naming.lookup查找遠程對象,然後調用該方法。然後這個方法實際上由to_Server_Impl在服務器上執行。所以該消息被打印在服務器上。 – Tudor 2011-12-22 11:28:58

+0

您是否需要關於RMI如何工作的解釋? – Tudor 2011-12-22 11:41:49

0

這是一個遠程對象。它在服務器上執行。它在服務器上輸出它的輸出。這就是RMI 的含義。如果它在客戶端輸出它的輸出,它必須是本地對象而不是遠程對象。