举2个例子:
1.BOSS要求提供JDBC,Hibernate,Ibatis等多套数据库操作解决方案,能够无成本地在这三个解决方案间切换。
2.系统的产品有多于一个的产品族,而系统只消费其中某一族的产品(Unix&Windows)
Button--->UnixButton/WinButton
Text----->UnixText/WinText
Unix产品族和Windows产品族,不会同时使用。
Factory--->UnixFactory/WinFactory
看类图吧:
BOOK产品:
public interface IBookDAO { public void drop(); public void save(); public void copy(); } public class MySQLBookDAO implements IBookDAO { public void copy() { System.out.println("copy book using the MySQL..."); } public void drop() { System.out.println("drop book using the MySQL..."); } public void save() { System.out.println("save book using the MySQL..."); } } public class SQLServerBookDAO implements IBookDAO { public void copy() { System.out.println("copy book using the sqlserver..."); } public void drop() { System.out.println("drop book using the sqlserver..."); } public void save() { System.out.println("save book using the sqlserver..."); } }
USER产品:
public interface IUserDAO { public void save(); public void delete(); public void get(); } public class MySQLUserDAO implements IUserDAO { public void delete() { System.out.println("delete user using the MySQL..."); } public void get() { System.out.println("get user using the MySQL..."); } public void save() { System.out.println("save user using the MySQL..."); } } public class SQLServerUserDAO implements IUserDAO { public void delete() { System.out.println("delete user using the sqlserver..."); } public void get() { System.out.println("get user using the sqlserver..."); } public void save() { System.out.println("save user using the sqlserver..."); } }
FACTORY:
public interface IFactory { public IUserDAO getUserDAO(); public IBookDAO getBookDAO(); } public class MySQLFactory implements IFactory { public IBookDAO getBookDAO() { return new MySQLBookDAO(); } public IUserDAO getUserDAO() { return new MySQLUserDAO(); } } public class SQLServerFactory implements IFactory { public IBookDAO getBookDAO() { return new SQLServerBookDAO(); } public IUserDAO getUserDAO() { return new SQLServerUserDAO(); } }
TEST:
public class Test { public static void main(String[] args) { IFactory factory = new SQLServerFactory(); factory.getUserDAO().delete(); factory.getBookDAO().copy(); } }
但是这里也有一个不好的地方,如果我在系统的各个地方都IFactory factory = new ...的话,假设new了100处,以后要换为MYSQLFactory的话,就得改100处地方。。所以可以抽象工厂+简单工厂来解耦。
抽象工厂的简单工厂类:
public class AbstractFactory { private static final String DB = "mysql"; public static IFactory getDataAcessFactory(){ IFactory factory = null; if("mysql".equals(DB)){ factory = new MySQLFactory(); }else if("sqlserver".equals(DB)){ factory = new SQLServerFactory(); }else{ throw new RuntimeException("No DB logic matched in the abstract factory."); } return factory; } }
客户端测试:
public class Test2 { public static void main(String[] args) { IFactory factory = AbstractFactory.getDataAcessFactory(); factory.getUserDAO().delete(); factory.getBookDAO().copy(); } }