在java中存在一种神奇的内部类,它叫做匿名内部类,它是内部类,也是接口实现类或子类(这里需要注意,一个匿名内部类只能实现一个接口或者继承一个类)。一般我们在写匿名内部类的时候,一般都是new MyClass(){ },这部分其实只是一个对象,它可以作为函数参数,函数返回值等等。虽然创建的是MyClass的对象(其实也可以是MyInterface),但是实际上它是继承(或者实现)类的对象,我们将继承(或者实现)类的定义,包括重写,重载,覆盖或者新的变量、函数的部分,放入了继承(或者实现)类的对象后面的大括号中,这是一种简写的方法,所以我们把它称作匿名内部类,因为它本质上是一个类,但是没有名字,使用的时候直接通过父类或者接口生成对象,将类的定义放入后面的大括号中。
下面我们介绍它在工厂方法中的使用:
public class Factories {
static void ServiceCousumer(ServiceFactory fact){
Service s=fact.getService();
s.method1();
s.method2();
}
public static void main(String args[]){
ServiceCousumer(Implementation1.fact);
ServiceCousumer(Implementation2.fact);
}
}
interface Service{
void method1();
void method2();
}
interface ServiceFactory{
Service getService();
}
class Implementation1 implements Service{
@Override
public void method1() {
// TODO Auto-generated method stub
System.out.println("Implementation1 method1");
}
@Override
public void method2() {
// TODO Auto-generated method stub
System.out.println("Implementation1 method2");
}
private Implementation1(){
}
static ServiceFactory fact=new ServiceFactory(){
@Override
public Service getService() {
// TODO Auto-generated method stub
return new Implementation1();
}
};
}
class Implementation2 implements Service{
@Override
public void method1() {
// TODO Auto-generated method stub
System.out.println("Implementation2 method1");
}
@Override
public void method2() {
// TODO Auto-generated method stub
System.out.println("Implementation2 method2");
}
private Implementation2(){
}
static ServiceFactory fact=new ServiceFactory(){
@Override
public Service getService() {
// TODO Auto-generated method stub
return new Implementation2();
}
};
}
这部分代码来自《Thinking in java》。
我们在代码中创建了两个具体的实现类,实现了Service接口,这两个类的对象是工厂类需要创建的对象。同时还有一个接口叫做ServiceFactory,它拥有一个函数,我们可以看出,这个函数是用来创建Service的,Service本质上是它的实现类实例。Service接口中有两个函数,method1和method2,他们是正常的接口的函数,没有特殊意义。如果换做普通的写法,我们需要创建针对每个Service的实现类创建ServiceFactory接口的实现类,通过不同ServiceFactory实现类中重写getService方法来完成工程类的职责。
但是使用匿名内部类的方法可以将每个ServiceFactory接口的实现类以静态内部类的方式作为每个Service的实现类的一个静态变量。我们在主函数中是这样调用的,创建一个函数,参数是ServiceFactory,在调用的时候,直接将Service的实现类的静态成员变量传入就行。在这个函数中通过这个变量的getService方法创建需要的变量。在这个函数中的变量形式都是以接口名的形式,但是本质上都是其实现类的变量。
对于这个静态变量,书上是这样的:你经常只需要单一的工厂对象(一个业务实现类只需要一个工厂对象),因此在本例中他被创建为业务实现类中的一个static域(static变量不需要创建业务类对象,直接类名就可以调用),这样产生的语法也更具有实际意义。