设计模式——抽象工厂模式

  为创建一组相关或相互依赖的对象提供一个接口,而且无需指定他们的具体类。

抽象工厂模式与工厂方法模式的区别

  抽象工厂模式是工厂方法模式的升级版本,他用来创建一组相关或者相互依赖的对象。他与工厂方法模式的区别就在于,工厂方法模式针对的是一个产品等级结构;而抽象工厂模式则是针对的多个产品等级结构。在编程中,通常一个产品结构,表现为一个接口或者抽象类,也就是说,工厂方法模式提供的所有产品都是衍生自同一个接口或抽象类,而抽象工厂模式所提供的产品则是衍生自不同的接口或抽象类
  在抽象工厂模式中,有一个产品族的概念:所谓的产品族,是指位于不同产品等级结构中功能相关联的产品组成的家族。抽象工厂模式所提供的一系列产品就组成一个产品族;而工厂方法提供的一系列产品称为一个等级结构。我们依然拿生产汽车的例子来说明他们之间的区别。

优点

  抽象工厂模式将具体产品的创建延迟到具体工厂的子类中,这样将对象的创建封装起来,可以减少客户端与具体产品类之间的依赖,从而使系统耦合度低,这样更有利于后期的维护和扩展,这真是抽象工厂模式的优点所在,然后抽象模式同时也存在不足的地方

缺点

  抽象工厂模式很难支持新种类产品的变化。这是因为抽象工厂接口中已经确定了可以被创建的产品集合,如果需要添加新产品,此时就必须去修改抽象工厂的接口,这样就涉及到抽象工厂类的以及所有子类的改变,这样也就违背了“开发——封闭”原则

 

实现

  借助女娲造人的过程添加新的物种等级水果,然后根据地域造不同的人。类图如下:

人类接口:

package com.lidaming.design03.abstractfactory;

public interface IHuman {
    void color();
    
}
View Code

人类的实现类:

package com.lidaming.design03.abstractfactory;

public class WhiteHuman implements IHuman {

    public void color() {
        System.out.println("this is white");

    }
}
View Code
package com.lidaming.design03.abstractfactory;

public class YellowHuman implements IHuman {

    public void color() {
        System.out.println("this is yellow");

    }

}
View Code

水果接口:

package com.lidaming.design03.abstractfactory;

public interface IFruit {
    void locate();
}
View Code

水果的实现类:

package com.lidaming.design03.abstractfactory;

public class Apple implements IFruit {

    public void locate() {
        System.out.println("grow on the tree");
    }

}
View Code
package com.lidaming.design03.abstractfactory;

public class Orange implements IFruit {

    public void locate() {
        // TODO Auto-generated method stub
        System.out.println("grow on the tree");
    }

}
View Code

抽象工厂:

package com.lidaming.design03.abstractfactory;

public interface AbstractFactory {
    IHuman createHuman();

    IFruit createFruite();
}
View Code

具体工厂的实现:

package com.lidaming.design03.abstractfactory;

public class AsiaFactory implements AbstractFactory {

    public IHuman createHuman() {
        
        try {
            return YellowHuman.class.newInstance();
        } catch (InstantiationException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        } catch (IllegalAccessException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }
        return null;
    }

    public IFruit createFruite() {
        try {
            return Apple.class.newInstance();
        } catch (InstantiationException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        } catch (IllegalAccessException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }
        return null;
    }

}
View Code
package com.lidaming.design03.abstractfactory;

public class Europe implements AbstractFactory {

    public IHuman createHuman() {
        try {
            return WhiteHuman.class.newInstance();
        } catch (InstantiationException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        } catch (IllegalAccessException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }
        return null;
    }

    public IFruit createFruite() {
        try {
            return Orange.class.newInstance();
        } catch (InstantiationException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        } catch (IllegalAccessException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }
        return null;
    }

}
View Code

场景类:

package com.lidaming.design03.abstractfactory;

public class Client {
    public static void main(String[] args) {
        AbstractFactory factory = new AsiaFactory();
        IHuman human = factory.createHuman();
        human.color();
        IFruit fruit = factory.createFruite();
        fruit.locate();

        factory = new Europe();
        human = factory.createHuman();
        human.color();
        fruit = factory.createFruite();
        fruit.locate();
    }
}
View Code

 

分析

当抽象工厂面对扩展新的产品等级的时候,如:造动物的时候!

  需要修改抽象工厂,具体工厂(违反“开放封闭原则”),至于维护成本,更是无法评估

总结

  无论是简单工厂模式,工厂方法模式,还是抽象工厂模式,他们都属于工厂模式,在形式和特点上也是极为相似的,他们的最终目的都是为了解耦。在使用时,我们不必去在意这个模式到底工厂方法模式还是抽象工厂模式,因为他们之间的演变常常是令人琢磨不透的。经常你会发现,明明使用的工厂方法模式,当新需求来临,稍加修改,加入了一个新方法后,由于类中的产品构成了不同等级结构中的产品族,它就变成抽象工厂模式了;而对于抽象工厂模式,当减少一个方法使的提供的产品不再构成产品族之后,它就演变成了工厂方法模式。
  所以,在使用工厂模式时,只需要关心降低耦合度的目的是否达到了。

 

参考:

http://blog.csdn.net/zhengzhb/article/details/7359385

http://blog.jobbole.com/78067/

posted @ 2016-04-12 11:44  无头咸鱼  阅读(223)  评论(0编辑  收藏  举报