到目前为止,我到处都看到创建空对象模式的步骤,例如在 BST 中删除空检查,如下所示:
创建接口节点
创建两个实现接口节点的类。其中一个是 real_Node,另一个是 null_Node。
使用这些类,可以在创建树时在 BST 类中删除空检查。
现在我想知道,有没有其他方法可以做到这一点,例如,我们可以实现空对象模式而不使用只使用类的接口,即在上面的步骤(1.)中我们可以使用 Node 类而不是 Node 接口吗
到目前为止,我到处都看到创建空对象模式的步骤,例如在 BST 中删除空检查,如下所示:
创建接口节点
创建两个实现接口节点的类。其中一个是 real_Node,另一个是 null_Node。
使用这些类,可以在创建树时在 BST 类中删除空检查。
现在我想知道,有没有其他方法可以做到这一点,例如,我们可以实现空对象模式而不使用只使用类的接口,即在上面的步骤(1.)中我们可以使用 Node 类而不是 Node 接口吗
是的,有一些方法可以在不显式使用 Java 的情况下实现 Null 对象模式interface
。但是,您确实在做同样的事情,所以 YMMV。如果您无权访问基类和/或它不允许某种形式的扩展/覆盖,您可能会发现问题。
创建一个扩展您的基类但通过覆盖它们来执行“空”操作的类。您通常会将其隐藏在某种静态构造函数后面以便于访问。
class Base {
public void someMethod() {
// this stuff does the non-null behaviour
}
public static Base nullVersion() {
return new NullOfBase();
}
private static class NullOfBase extends Base {
@Override
public void someMethod() {
// this guy does the null version.
}
}
}
在静态“NULL”类成员上使用匿名类,它会覆盖您需要覆盖的各种操作。
public class Base {
public static final Base NULL = new Base() {
@Override
public void someMethod() {
// this guy does the null version.
}
}
public void someMethod() {
// this stuff does the non-null behaviour
}
}
使用抽象类来保存非空实现和空实现通用的操作,将这些方法标记为最终方法,所有其他方法都是抽象的并在两个具体类中实现——一个用于非空功能,另一个用于空功能。您可以使用静态构造函数来使常见用例易于构造并隐藏具体的类名。
public abstract class Base {
public final sayHello() {
System.out.println("Hello world");
}
public abstract void someMethod();
public static Base nonNullVersion() {
return new NonNullBase();
}
public static Base nullVersion() {
return new NullBase();
}
private static final class NonNullBase extends Base {
@Override
public void someMethod() {
// this stuff does the non-null behaviour
}
}
private static final class NullBase extends Base {
@Override
public void someMethod() {
// this stuff does the null behaviour
}
}
}
或者,有时 NULL 对象实际上只是特定值的特例(它实际上取决于类上的操作是什么)。在这种情况下,您可以拥有具有该值的静态成员或允许您创建它的静态工厂。