工厂指的是创建对象的工厂,工厂模式是一种创建对象的模式,使用factory.createXXX你就能获得想要的对象。那么为什么要使用工厂模式呢?有很多足够重要的理由:
- 实际开发中很多情况并不能只用一句new就能得到想要的对象。熟悉的比如spring中各种bean之间的相互依赖,你要得到一个service,不光只new service,还需要new 业务逻辑对象,new dao对象。所以spring使用factoryBean来封装了对象的创建过程。即工厂模式把对象创建的复杂过程封装,达到灵活,解耦的目的。
- 工厂在提供对象时可能会灵活的创建父类的不同子类实现,比如存储小量数组而提供Class1,数组两过大时就提供Class2,甚至可以返回代理对象。随时也可更换这种创建逻辑。这也是简单的new所不具备的。
- 工厂在提供对象给使用者时,不会像new一样每次必须创建新的对象。在工厂模式的内部写法中可以将之前已经创建好的对象返回出去。这对于系统中对象的管理极其重要。
总之一句话,通过封装,可以将提供对象的方式变得多种多样,强大且灵活。使用对象的人不需要知道创建对象的细节,从而得到的好处多多。
工厂模式有三种,简单工厂模式,工厂模式,抽象工厂模式:
1.简单工厂模式:
a.产品抽象成接口,同时可存在1个或多个产品实现类。
b.只有一个工厂类,而且一般会使用静态方法来创建产品。因为只有一个工厂类,所以需要给创建方法传递产品实现类的具体参数,来创建不同的产品实现。
c.如果有产品实现类有增减,那就必须改动这个工厂类的创建代码。
interface ICar{}
class Car1 implements ICar{
}
class Car2 implements ICar{}
class Factory{
public static ICar createCar(int type){
if(type==1)
return new Car1();
if(type==2)
return new Car2();
}
}
2.工厂模式:
a.同一类产品抽象成一个接口,同时可存在1个或多个产品实现类
b.工厂抽象成接口,同时可存在1个或多个工厂实现,每一个工厂实现,只对应一种具体产品实现的创建。
c.如果产品实现类有增减,那么对应的增减工厂实现即可。扩展性好。
interface ICar{}
class Car implements ICar{
public Car(Engine e, Underpan u, Wheel w){
....
}
}
interface IFactory {
public ICar createCar();
}
class Factory implements IFactory {
public ICar createCar() {
Engine engine = new Engine();
Underpan underpan = new Underpan();
Wheel wheel = new Wheel();
ICar car = new Car(underpan, wheel, engine);
return car;
}
}
public class Client {
public static void main(String[] args) {
IFactory factory = new Factory();
ICar car = factory.createCar();
car.show();
}
}
3.抽象工厂模式:引入了产品族和产品树的概念。打一个不恰当的比喻,List和Map,分别有LinkedList和LinkedHashMap,有ArrayList和HashMap。 那么:
a. 不同类产品抽象成不同接口即List和Map,同时可存在1个或多个产品实现类
b.不同工厂抽象成不同的工厂接口,同时可存在1个或多个工厂实现,每一个工厂实现,会提供一类有共性的产品族的创建方法。例如一个工厂实现,负责创建LinkedList和LinkedHashMap这两个有共性的产品。
c.如果产品实现有增减,抽象工厂模式的工厂实现同样需要修改代码。
d.这种模式的意义在于,对于非常多种类的产品,通过不同的工厂实现来定义出不同产品之间的关联和约束。
interface ICar1 {
public void show();
}
interface ICar2 {
public void show();
}
class Car1TypeA implements ICar1 {
public void show() {
System.out.println("这是1型产品的TypeA");
}
}
class Car2TypeA implements ICar2 {
public void show() {
System.out.println("这是2型产品的TypeA");
}
}
interface IFactoryTypeA {
public ICar1 createCar1TypeA();
public ICar2 createCar2TypeA();
}
class TypeAFactory implements IFactoryTypeA{
public ICar1 createCar1TypeA() {
return new Car1TypeA();
}
public ICar2 createCar2TypeA() {
return new Car2TypeA();
}
}
//同时可能会出现TypeB类型的Car1和Car2的产品实现,并有TypeB的工厂接口和工厂实现类来负责创建他们
....
个人认为三种工厂模式的设计理念是基本一致的,其实没有特别必要去死记或纠结于三种工厂的区别,重要的是在实际使用中能够考虑到封装和解耦的精髓,自然的采用合适的工厂实现就行了,是工厂还是抽象工厂,是顺其自然水到渠成的事情。