EJB 组件的一个比较常见的用途是在关系型数据治理领域。与 RMI 结合起来,EJB 组件让您不必钻研 JDBC 就可以从关系数据库访问数据。但这种抽象是要付出代价的:RMI 很慢,通常是极慢。那么,窍门就是找到一种方法来保持 EJB 技术的所有优点而又没有使用 RMI 的巨大开销。在这篇技巧文章中,您将看到值对象(也称为对象映射)是如何帮助您绕开最严重的 RMI 速度障碍的。您将首先从一个工作示例开始,然后了解代码是怎样工作的。
简单实体 bean
考虑一个名为 DVDs 的简单数据库表。这个表有几列:id、title、releaseDate、PRodUCer(通过外键)和 Director(也是通过外键)。因为我们正在使用 EJB 组件,所以表由实体 bean 表示,并且每个列都有其自己的取值(accessor)方法和赋值(mutator)方法。清单 1 显示了我们的 DVD 表的远程接口:
清单 1. DVD 远程接口
import com.ibm.ejb;
import java.rmi.RemoteException;
import java.util.Date;
import javax.ejb.EJBObject;
public interface DVD extends EJBObject {
public int getId() throws RemoteException;
public String getTitle() throws RemoteException;
public void setTitle(String title) throws RemoteException;
public Date getReleaseDate() throws RemoteException;
public void setReleaseDate(Date releaseDate) throws RemoteException;
public Person getProducer() throws RemoteException;
public void setProducer(Person producer) throws RemoteException;
public Person getDirector() throws RemoteException;
public void setDirector(Person director) throws RemoteException;
}
这里的问题是如何访问表数据,可能一次访问所有数据。为进行一次 DVD 销售或搜索,在线商店或清单应用程序很可能要求获取上述列中包含的大多数或所有信息。为了访问所有信息,应用程序为每列调用一个取值方法 ? 共有五次方法调用,每次都会多占用一点 RMI 通信时间。这种情况再加上其它复杂性,如可能的错误情况、网络流量和相关问题,以及数据的指数级数量(大多数此类表有 15 行或更多),我们的应用程序随时都可能崩溃。
这时就需要值对象。值对象是简单的 Java 类,可以用它来表示多种对象,包括关系数据库行中的数据。通过直接使用值对象,而不是反复使用 bean 的远程接口,我们可以将 RMI 通信减少到一次方法调用。
创建值对象
清单 2 中的值对象看起来和我们的远程接口几乎相同,但它实际上是具体类。注:通常用 bean 的名称加上 Info 来表示值对象。
清单 2. DVD 值对象
package com.ibm.ejb;
import java.io.Serializable;
import java.util.Date;
public class DVDInfo implements Serializable {
private int id;
private String title
private Date releaseDate;
private Producer producer;
private Director director;
public int getId() {return id;
}
void setId(int id) {this.id = id;
}public String getTitle() {return title;
}
public void setTitle(String title) {this.title = title;
}
public Date getReleaseDate() {return releaseDate;
}
public void setReleaseDate(Date releaseDate) {
this.releaseDate = releaseDate;
}
public Person getProducer() {
return producer;
}
public void setProducer(Person producer) {this.producer = producer;
}
public Person getDirector() {return director;
}
public void setDirector(Person director) {this.director = director;
}}
新闻热点
疑难解答