什么是工厂?我为什么要用?
抽象工厂模式
工厂模式有两种不同类型:工厂方法模式和抽象工厂模式。你指的是哪一个?
你熟悉JDBC吗?它是一个抽象的工厂。这是一个很好的现实例子。
// Factory method. Loads the driver by given classname. It actually returns a
// concrete Class. However, we don't need it here, so we just ignore it.
// It can be any driver class name. The MySQL one here is just an example.
// Under the covers, it will do DriverManager.registerDriver(new Driver()).
Class.forName("com.mysql.jdbc.Driver");
// Abstract factory. This lets the driver return a concrete connection for the
// given URL. You can just declare it against java.sql.Connection interface.
// Under the covers, the DriverManager will find the MySQL driver by URL and call
// driver.connect() which in turn will return new ConnectionImpl().
Connection connection = DriverManager.getConnection(url);
// Abstract factory. This lets the driver return a concrete statement from the
// connection. You can just declare it against java.sql.Statement interface.
// Under the covers, the MySQL ConnectionImpl will return new StatementImpl().
Statement statement = connection.createStatement();
// Abstract factory. This lets the driver return a concrete result set from the
// statement. You can just declare it against java.sql.ResultSet interface.
// Under the covers, the MySQL StatementImpl will return new ResultSetImpl().
ResultSet resultSet = statement.executeQuery(sql);
您的代码中不需要有一行特定于JDBC驱动程序的import。你不需要做任何事情。你只需申报所有针对java.sql.*的东西。你不需要自己动手。您只需要从一个抽象工厂获得它作为标准API的一部分。
如果将JDBC驱动程序类名称命名为可以在外部配置的变量(例如,属性文件),并编写ANSI兼容SQL查询,那么您就不必为世界所知的每一个数据库供应商和/或JDBC驱动程序重写、重新编译、重建和重新分配Java应用程序。您只需在运行时类路径中删除所需的JDBC驱动程序JAR文件,并提供一些(属性)文件的配置,而不需要更改任何Java代码行,只要您想切换DB或在不同的DB上重用应用程序。
这就是接口和抽象工厂的力量。
另一个已知的真实世界例子是JavaEE。将"JDBC"与"JavaEE"和"JDBC驱动程序"替换为"JavaEE应用服务器"(FielF飞、TomEE、GelasFISH、Reland等)。参见:
Class#forName()和DriverManager#getConnection()的工作原理是什么?
JavaEE究竟是什么?
维基百科:工厂方法模式
维基百科:抽象工厂模式
简单地说,工厂是一个面向对象的设计模式,它处理创建对象,而不指定要创建的对象的确切类。
在维基百科中有一个很好的理由来使用它:
The creation of an object often requires complex processes not
appropriate to include within a composing object. The object's
creation may lead to a significant duplication of code, may require
information not accessible to the composing object, may not provide a
sufficient level of abstraction, or may otherwise not be part of the
composing object's concerns. The factory method design pattern handles
these problems by defining a separate method for creating the objects,
which subclasses can then override to specify the derived type of
product that will be created.
+1:当可以推断类,但其他细节(如构造函数参数)隐藏时,也可以使用工厂。一个工厂创建一个对象,而该工厂的调用方不需要知道有关如何完成此操作的任何详细信息。
当您需要在运行时创建一个对象的多个实例时,工厂设计模式是理想的。您可以初始化许多实例,而不是显式地创建每个实例。此外,还可以封装可多次重复使用的复杂创建代码。
例子:
public class Person {
int ID;
String gender;
public Person(int ID,String gender){
this.ID=ID;
this.gender=gender;
}
public int getID() {
return ID;
}
public String getGender() {
return gender;
}
}
public class PersonFactory{
public static Person createMale(int id){
return new Person(id,"M");
}
public static Person createFemale(int id){
return new Person(id,"F");
}
}
public class factorytest{
public static void main(String[]args){
Person[] pList= new Person[100];
for(int x=0;x<100;x++){
pList[x]=PersonFactory.createMale(x);
}
}
}
在这个例子中,我们封装了gender初始化参数的详细信息,并且可以简单地要求personFactory创建male或createwome person对象。
举个容易理解的例子
What is a factory ?
维基百科详细解释
也可以在这里看到传奇的Balusc关于许多gof模式示例的答案。简单来说,工厂创建初始化分配可以在代码中使用的对象。例如,如果您有一个Person抽象类或接口,甚至是一个具体的类,并且您在另一个类(如private person;中)中声明了它,那就是该对象已经声明,但尚未创建。您将使用新的或某些依赖项注入或工厂来创建此对象(还有其他选项,例如定位器等)。
Why would I want to use one?
现在你可能需要一个特定类型的人,例如老师,甚至是人,可能有不同的植入,基于不同的配置等。工厂模式负责这一点。它允许你或者我应该说,让你不用担心应该使用什么实现或初始化特定的类。
工厂是用于创建其他对象的对象。
它创建对象,而不向客户机公开实例化逻辑。
当您不想向客户机/调用者公开对象实例化逻辑时,使用此模式
相关员额:
设计模式:工厂vs工厂方法vs抽象工厂
工厂模式和抽象工厂模式的基本区别是什么?
工厂是一个创建对象的对象。常见用法包括两种情况:
当您希望将具体对象的选择委托给工厂时,例如,它可以返回已经存在的对象(参见EDCOX1×0),这是所谓的工厂方法,或者根据一些条件选择具体的实现方式——例如提供的参数或预定义的选项(参见Java API中的EDCOX1 OR 1类XML处理)
当你想要更灵活的工作时。不能将方法或构造函数作为参数传递(当然可以,但反射很糟糕),因此可以使用具体工厂作为对象源(例如,泛型方法中的SomeFactory)。