简单来说,要实现A机器上JVM上运行的Java程序,远程调用B机器上JVM上的Java程序,计算完毕,返回给A机器。
在没有RMI的情况下,我们使用普通的网络传输技术能完成么?当然,两种选择,Socket直接通讯,将参数传给B,B在通过Socket返还给调用者。或者通过Servlet也可以远程调用阿。
那么这样解决问题时没有问题,但对于A和B来说,代码量、程序复用程序、维护性都不会太理想。
如果能让调用者不知道网络操作,实现对于用户透明,也就是像调用本地一样,对象名.方法名。
那么就是RMI规范涉及到一些接口。
面向接口的编程方式,就可以达到代码的实现与声明分离。
这样用户就只关心接口了。很多细节让遵守规范(也就是一些编写好的工具)的实现类去完成吧。[就是Stub和Skeleton]
那么就先定一个用户A要知道怎么用,B要知道方法签名完成实现,的同一接口吧。
import java.rmi.*;


public interface Compute extends Remote
{
public double add(double a,double b) throws RemoteException;
}两点要求
1,继承标记接口Remote。
identify interfaces whose methods may be invoked from a non-local virtual machine.
标识该接口可以被非本地VM调用呗。
2,里面每个方法都要抛出RemoteException
业务接口的实现类,也就是做实事的类
import java.rmi.server.*;
import java.rmi.*;

public class ComputeImpl extends UnicastRemoteObject implements Compute


{
//要在构造方法抛出异常

public ComputeImpl() throws RemoteException
{}

public double add(double a,double b)
{
return a+b;
}
}=====================
javac *.class
rmic -keep ComputeImpl
带参数,可以保留Stub和Skeleton源码。
通过ComputeImpl的实现类来生成负责通讯的Stub(存根)和Skeleton(框架)
======================
那么就是要把这个对象绑定到一个端口上。
以便别人来使用
编写一个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别名
}

}客户端
import java.rmi.*;

public class Client


{
public static void main(String[] args) throws Exception

{
Compute c = (Compute)Naming.lookup("rmi://localhost:8888/compute");//rmiregistry首先响应
//实际c是Stub对象
System.out.println(c.getClass());
System.out.println(c.add(12.3,34));
}
} 看到没有,客户端通过rmi协议到服务器上寻找/compute资源对象。那个Naming是RMI专用,不是JNDI。
那么Server类并没有负责监听阿。
哦,最后有一个强大的工具在JAVA_HOME/bin/下,叫做rmiregistry,专门负责监听固定端口上,rmi协议的请求。
=================
rmiregistry 8888
=================
启动Server,绑定远程对象阿
java Server
=================
启动一个Client,调用一下
java Client
=================

===============
另外一些小问题
由于rmiregistry 工具的不断强大,jdk1.4已经可以不再使用skeleton,到1.5,根本就不生成skeleton了。
rmiregistry可以充当skeleton角色完成功能。
记住EJB中,还不行,因为没有rmiregistry工具了。呵呵,明白了?
=========================
所以什么呢,RMI就是一种代理模式的应用Stub,就是实际实现类的客户代理。
但需要统一的接口,才能对于用户、调用者透明啊!
------------------------
我说的比较通俗。还有很多深刻的东西。
posted on 2006-03-19 22:42
北国狼人的BloG 阅读(1333)
评论(0) 编辑 收藏 所属分类:
达内学习总结