在项目中的facade都需要对传入的参数进行相关的判断,或者对对象的进行判断,从人防止空指针的发生。
eg: public Book getBook(int id) {
if (id < 0) {
return null;
}
return new Book(1, "java编程思想", 65);
}
或者
List<Book> list =BookDao.getBook()
if (null != list && list.isEmpty())
{
return mappings.get(0);
}
return null;
在调用的时候我们需要进行book对象的判断
if(null==book)
{
....
}else{....}
系统在使用对象的相关功能时,总要检查对象是否为null,如果不为null,我们才会调用它的相关方法,完成某种逻辑。这样的检查在一个系统中出现很多次,相信任何一个设计者都不愿意看到这样的情况。为了解决这种问题,我们可以可以引入空对象,这样,我们就可以摆脱大量程式化的代码,对代码的可读性也是一个飞跃。
方法1 : 采用的传统的方式但参数不合法时抛出相关的异常信息,那么上述例子可以为如下:
if (id < 0)
{
throw new IllegalArgumentException("Invalidate id ");
}
那么在调用时无需判断返回的对象是否为空操作了。
方法2 : 我们可以采用apache 中的Validate类中的方法对参数进行校验,对对象进行为空判断等,上述的代码可以修改为
public Book getBook(int id) {
Validate.isTrue(BigDecimal.valueOf(id).compareTo(BigDecimal.ZERO) >0, "Invalidate id ");
return new Book(1, "java Design Pattern", 100);
}
那么在调用时无需判断返回的对象是否为空操作了,如果参数为-1不合法那么Exception in thread "main" java.lang.IllegalArgumentException: Invalidate id 等信息。
方式1和方式2的唯一区别在于方式2少了条件的判断语句,其大体的还是与第一种方式基本相同。
方法3:我们可以采用NullObject模式来解决该问题,具体实现如下:
a. 编写Nullable接口,该接口中包含了isNull方法。
public interface Nullable<T> {
boolean isNull();
}
b.编写Nullbook实现实体类Book,并重写isNull方法。
class NullBook extends Book {
@Override
public boolean isNull() {
return true;
}
}
c.修改Book实体类将其实现Nullable接口,并编写工厂方法返回book对象。
//该方法返回值为false
@Override
public boolean isNull() {
return false;
}
//工厂方法,返回book对象
public static Book createNullBook() {
return new NullBook();
}
那么Bookservice中的方法可以修改如下:
public Book getBook(int id) {
if (id < 0) {
return Book.createNullBook();
}
return new Book(1, "java编程思想", 65);
}
调用Bookservice的方法可以修改为:
BookService service = new BookService();
Book book = service.getBook(-1);
if (book.isNull()) {
System.out.println("book not found!");
} else {
System.out.println("name:" + book.getName());
System.out.println("price:" + book.getPrice());
}
方法3可能会出现一个问题:如果某系统中大量的实体对象都需要进行Null判断,那么如果对某个实体都添加一个NullXX的类,那么这样会导致大量的类产生,也会有一定的影响。
目前解决的方法是将NullXX类做为实体类的内部类,从而来减少类的个数,完成NullObject模式。 可以将Book修改为如下:
public class Book
{
.....
static class NullBook extends Book {
@Override
public boolean isNull() {
return true;
}
.....
}
总结 :方法1和方法2适应于系统中对该对象判断为null的情况下出现的比较少,如果该对象为null判断出现的非常频繁,那么方法3应该是不错的选择。