工厂方法(actory Method)与抽象工厂方法(Abstract Factory)

本文深入探讨了工厂方法和抽象工厂两种设计模式。工厂方法通过定义创建对象的接口,让子类决定实例化哪个类,实现了对象创建与使用的分离。抽象工厂则进一步提供了创建一系列相关或相互依赖对象的接口,无需指定具体类,适用于创建产品族。文章通过实例代码展示了两种模式的实现方式。

首先来看工厂方法(actory Method)

定义:
定义一个用于创建对象的接口,让子类决定实例化哪一个类。Factory Method使一个类的实例化延迟到其子类。

工厂方法的目的是使得创建对象和使用对象是分离的,并且客户端总是引用抽象工厂和抽象产品:
在这里插入图片描述

举例说明:
首先定义一个工厂接口:

public interface Factory {
   public Product createProduct();
}
public class FactoryImpl implements Factory {
    public Product createProduct(){
    	return new ProductImpl();
    }
}

客户端:

Product product = new FactoryImpl.createProduct();

当然我们也可以在工厂接口中构建一个静态方法返回子类实例:
工厂接口:

public interface Factory {
	static Factory impl = new FactoryImpl();
    // 创建方法:
    public Product createProduct();
    // 获取工厂实例:
    static Factory getFactory() {
        return impl;
    }
}

客户端:

Factory factory = Factory.getFactory();
Product product = fanctory.createProduct();

静态工厂方法:

public class Factory {
    public static Product createProduct() {
        return new ProductImpl();
    }
}
Product p = Factory.createProduct();

注意:
工厂方法可以隐藏创建产品的细节,且不一定每次都会真正创建产品,完全可以返回缓存的产品,从而提升速度并减少内存消耗。

————————————————————————————————————————

我们接下来看一下抽象工厂方法(Abstract Factory):

定义:
提供一个创建一系列相关或相互依赖对象的接口,而无需指定它们具体的类。

在这里插入图片描述

一个具体类图实例:
在这里插入图片描述
抽象工厂方法创建的不是一个完整产品,而是“产品族”(遵循
固定搭配规则的多类产品的实例),得到的结果是:多个不同产品的
object,各产品创建过程对client可见,但“搭配”不能改变。

//AbstractProduct
public interface Window{
	public void setTitle(String s);
	public void repaint();
	public void addScrollbar(); 
}
//ConcreteProductA1
public class PMWindow implements Window{
	public void setTitle(){}
	public void repaint(){}
}
//ConcreteProductA2
public class MotifWindow implements Window{
	public void setTitle(){}
	public void repaint(){}
}
//AbstractFactory
public interface AbstractWidgetFactory{
	public Window createWindow();
	public Scrollbar createScrollbar();
}
//ConcreteFactory1
public class WidgetFactory1 implements AbstractWidgetFactory{
	public Window createWindow(){
		return new PMWindow();
	}
	public Scrollbar createScrollbar(){A}
}
//ConcreteFactory2
public class WidgetFactory2 implements AbstractWidgetFactory{
	public Window createWindow(){
		return new MotifWindow();
	}
	public Scrollbar createScrollbar(){B}

客户端:

AbstractWidgetFactory widgetFactory = null;
if(“Motif”)
	widgetFactory = new WidgetFactory2();
else
	widgetFactory = new WidgetFactory1();
Window window = widgetFactory.createWindow();
Scrollbar scrollbar = widgetFactory.createScrollbar();

总结:
抽象工厂模式是为了让创建工厂和一组产品与使用相分离,并可以随时切换到另一个工厂以及另一组产品;
抽象工厂模式实现的关键点是定义工厂接口和产品接口,但如何实现工厂与产品本身需要留给具体的子类实现,客户端只和抽象工厂与抽象产品打交道。

2025-07-06 15:01:52.812 [main] WARN o.s.b.w.s.c.AnnotationConfigServletWebServerApplicationContext:599 - Exception encountered during context initialization - ca ncelling refresh attempt: org.springframework.beans.factory.UnsatisfiedDependencyException: Error creating bean with name 'dictTableWhiteListHandlerImpl': Unsatis fied dependency expressed through field 'sysTableWhiteListService'; nested exception is org.springframework.beans.factory.UnsatisfiedDependencyException: Error cr eating bean with name 'sysTableWhiteListServiceImpl': Unsatisfied dependency expressed through field 'baseMapper'; nested exception is org.springframework.beans.f actory.UnsatisfiedDependencyException: Error creating bean with name 'sysTableWhiteListMapper' defined in URL [jar:file:/D:/新建文件夹/JeecgBoot-master/jeecg-boot /jeecg-module-system/jeecg-system-start/target/jeecg-system-start-3.8.1.jar!/BOOT-INF/lib/jeecg-system-biz-3.8.1.jar!/org/jeecg/modules/system/mapper/SysTableWhit eListMapper.class]: Unsatisfied dependency expressed through bean property 'sqlSessionTemplate'; nested exception is org.springframework.beans.factory.BeanCreatio nException: Error creating bean with name 'quartzDataSourceScriptDatabaseInitializer' defined in class path resource [org/springframework/boot/autoconfigure/quart z/QuartzAutoConfiguration$JdbcStoreTypeConfiguration.class]: Bean instantiation via factory method failed; nested exception is org.springframework.beans.BeanInsta ntiationException: Failed to instantiate [org.springframework.boot.autoconfigure.quartz.QuartzDataSourceScriptDatabaseInitializer]: Factory method 'quartzDataSourceScriptDatabaseInitializer' threw exception; nested exception is java.lang.IllegalStateException: Unable to detect database type 2025-07-06 15:01:52.813 [main] INFO c.b.dynamic.datasource.DynamicRoutingDataSource:211 - dynamic-datasource start closing .... 2025-07-06 15:01:52.814 [main] INFO com.alibaba.druid.pool.DruidDataSource:1880 - {dataSource-1} closing ... 2025-07-06 15:01:52.819 [main] INFO com.alibaba.druid.pool.DruidDataSource:1953 - {dataSource-1} closed 2025-07-06 15:01:52.820 [main] INFO c.b.dynamic.datasource.DynamicRoutingDataSource:215 - dynamic-datasource all closed success,bye 2025-07-06 15:01:52.856 [main] INFO o.s.b.a.l.ConditionEvaluationReportLoggingListener:136 - Error starting ApplicationContext. To display the conditions report re-run your application with 'debug' enabled. 2025-07-06 15:01:52.899 [main] ERROR org.springframework.boot.SpringApplication:818 - Application run failed org.springframework.beans.factory.UnsatisfiedDependencyException: Error creating bean with name 'dictTableWhiteListHandlerImpl': Unsatisfied dependency expressed through field 'sysTableWhiteListService'; nested exception is org.springframework.beans.factory.UnsatisfiedDependencyException: Error creating bean with name 'sys TableWhiteListServiceImpl': Unsatisfied dependency expressed through field 'baseMapper'; nested exception is org.springframework.beans.factory.UnsatisfiedDependen cyException: Error creating bean with name 'sysTableWhiteListMapper' defined in URL [jar:file:/D:/新建文件夹/JeecgBoot-master/jeecg-boot/jeecg-module-system/jeecg -system-start/target/jeecg-system-start-3.8.1.jar!/BOOT-INF/lib/jeecg-system-biz-3.8.1.jar!/org/jeecg/modules/system/mapper/SysTableWhiteListMapper.class]: Unsati sfied dependency expressed through bean property 'sqlSessionTemplate'; nested exception is org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'quartzDataSourceScriptDatabaseInitializer' defined in class path resource [org/springframework/boot/autoconfigure/quartz/QuartzAutoConfiguration$ JdbcStoreTypeConfiguration.class]: Bean instantiation via factory method failed; nested exception is org.springframework.beans.BeanInstantiationException: Failed to instantiate [org.springframework.boot.autoconfigure.quartz.QuartzDataSourceScriptDatabaseInitializer]: Factory method 'quartzDataSourceScriptDatabaseInitializer' threw exception; nested exception is java.lang.IllegalStateException: Unable to detect database type at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor$AutowiredFieldElement.resolveFieldValue(AutowiredAnnotationBeanPostProcessor.java:713) at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor$AutowiredFieldElement.inject(AutowiredAnnotationBeanPostProcessor.java:693) at org.springframework.beans.factory.annotation.InjectionMetadata.inject(InjectionMetadata.java:119) at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor.postProcessProperties(AutowiredAnnotationBeanPostProcessor.java:408) at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.populateBean(AbstractAutowireCapableBeanFactory.java:1431) at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:619) at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:542) at org.springframework.beans.factory.support.AbstractBeanFactory.lambda$doGetBean$0(AbstractBeanFactory.java:335) at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:234) at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:333) at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:208) at org.springframework.beans.factory.support.DefaultListableBeanFactory.preInstantiateSingletons(DefaultListableBeanFactory.java:955) at org.springframework.context.support.AbstractApplicationContext.finishBeanFactoryInitialization(AbstractApplicationContext.java:929) at org.springframework.context.support.AbstractApplicationContext.refresh(AbstractApplicationContext.java:591) at org.springframework.boot.web.servlet.context.ServletWebServerApplicationContext.refresh(ServletWebServerApplicationContext.java:147) at org.springframework.boot.SpringApplication.refresh(SpringApplication.java:732) at org.springframework.boot.SpringApplication.refreshContext(SpringApplication.java:409) at org.springframework.boot.SpringApplication.run(SpringApplication.java:308) at org.jeecg.JeecgSystemApplication.main(JeecgSystemApplication.java:36) at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method) at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:77) at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43) at java.base/java.lang.reflect.Method.invoke(Method.java:568) at org.springframework.boot.loader.MainMethodRunner.run(MainMethodRunner.java:49) at org.springframework.boot.loader.Launcher.launch(Launcher.java:108) at org.springframework.boot.loader.Launcher.launch(Launcher.java:58) at org.springframework.boot.loader.JarLauncher.main(JarLauncher.java:65) Caused by: org.springframework.beans.factory.UnsatisfiedDependencyException: Error creating bean with name 'sysTableWhiteListServiceImpl': Unsatisfied dependency expressed through field 'baseMapper'; nested exception is org.springframework.beans.factory.UnsatisfiedDependencyException: Error creating bean with name 'sysTabl eWhiteListMapper' defined in URL [jar:file:/D:/新建文件夹/JeecgBoot-master/jeecg-boot/jeecg-module-system/jeecg-system-start/target/jeecg-system-start-3.8.1.jar!/ BOOT-INF/lib/jeecg-system-biz-3.8.1.jar!/org/jeecg/modules/system/mapper/SysTableWhiteListMapper.class]: Unsatisfied dependency expressed through bean property 's qlSessionTemplate'; nested exception is org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'quartzDataSourceScriptDatabaseInit ializer' defined in class path resource [org/springframework/boot/autoconfigure/quartz/QuartzAutoConfiguration$JdbcStoreTypeConfiguration.class]: Bean instantiati on via factory method failed; nested exception is org.springframework.beans.BeanInstantiationException: Failed to instantiate [org.springframework.boot.autoconfig ure.quartz.QuartzDataSourceScriptDatabaseInitializer]: Factory method 'quartzDataSourceScriptDatabaseInitializer' threw exception; nested exception is java.lang.IllegalStateException: Unable to detect database type at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor$AutowiredFieldElement.resolveFieldValue(AutowiredAnnotationBeanPostProcessor.java:713) at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor$AutowiredFieldElement.inject(AutowiredAnnotationBeanPostProcessor.java:693) at org.springframework.beans.factory.annotation.InjectionMetadata.inject(InjectionMetadata.java:119) at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor.postProcessProperties(AutowiredAnnotationBeanPostProcessor.java:408) at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.populateBean(AbstractAutowireCapableBeanFactory.java:1431) at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:619) at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:542) at org.springframework.beans.factory.support.AbstractBeanFactory.lambda$doGetBean$0(AbstractBeanFactory.java:335) at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:234) at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:333) at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:208) at org.springframework.beans.factory.config.DependencyDescriptor.resolveCandidate(DependencyDescriptor.java:276) at org.springframework.beans.factory.support.DefaultListableBeanFactory.doResolveDependency(DefaultListableBeanFactory.java:1391) at org.springframework.beans.factory.support.DefaultListableBeanFactory.resolveDependency(DefaultListableBeanFactory.java:1311) at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor$AutowiredFieldElement.resolveFieldValue(AutowiredAnnotationBeanPostProcessor.java:710) ... 26 common frames omitted Caused by: org.springframework.beans.factory.UnsatisfiedDependencyException: Error creating bean with name 'sysTableWhiteListMapper' defined in URL [jar:file:/D:/ 新建文件夹/JeecgBoot-master/jeecg-boot/jeecg-module-system/jeecg-system-start/target/jeecg-system-start-3.8.1.jar!/BOOT-INF/lib/jeecg-system-biz-3.8.1.jar!/org/je ecg/modules/system/mapper/SysTableWhiteListMapper.class]: Unsatisfied dependency expressed through bean property 'sqlSessionTemplate'; nested exception is org.spr ingframework.beans.factory.BeanCreationException: Error creating bean with name 'quartzDataSourceScriptDatabaseInitializer' defined in class path resource [org/sp ringframework/boot/autoconfigure/quartz/QuartzAutoConfiguration$JdbcStoreTypeConfiguration.class]: Bean instantiation via factory method failed; nested exception is org.springframework.beans.BeanInstantiationException: Failed to instantiate [org.springframework.boot.autoconfigure.quartz.QuartzDataSourceScriptDatabaseInitia lizer]: Factory method 'quartzDataSourceScriptDatabaseInitializer' threw exception; nested exception is java.lang.IllegalStateException: Unable to detect database type at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.autowireByType(AbstractAutowireCapableBeanFactory.java:1534) at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.populateBean(AbstractAutowireCapableBeanFactory.java:1417) at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:619) at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:542) at org.springframework.beans.factory.support.AbstractBeanFactory.lambda$doGetBean$0(AbstractBeanFactory.java:335) at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:234) at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:333) at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:208) at org.springframework.beans.factory.config.DependencyDescriptor.resolveCandidate(DependencyDescriptor.java:276) at org.springframework.beans.factory.support.DefaultListableBeanFactory.doResolveDependency(DefaultListableBeanFactory.java:1391) at org.springframework.beans.factory.support.DefaultListableBeanFactory.resolveDependency(DefaultListableBeanFactory.java:1311) at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor$AutowiredFieldElement.resolveFieldValue(AutowiredAnnotationBeanPostProcessor.java:710) ... 40 common frames omitted Caused by: org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'quartzDataSourceScriptDatabaseInitializer' defined in class pat h resource [org/springframework/boot/autoconfigure/quartz/QuartzAutoConfiguration$JdbcStoreTypeConfiguration.class]: Bean instantiation via factory method failed; nested exception is org.springframework.beans.BeanInstantiationException: Failed to instantiate [org.springframework.boot.autoconfigure.quartz.QuartzDataSourceSc riptDatabaseInitializer]: Factory method 'quartzDataSourceScriptDatabaseInitializer' threw exception; nested exception is java.lang.IllegalStateException: Unable to detect database type at org.springframework.beans.factory.support.ConstructorResolver.instantiate(ConstructorResolver.java:653) at org.springframework.beans.factory.support.ConstructorResolver.instantiateUsingFactoryMethod(ConstructorResolver.java:633) at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.instantiateUsingFactoryMethod(AbstractAutowireCapableBeanFactory.java:1352) at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBeanInstance(AbstractAutowireCapableBeanFactory.java:1195) at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:582) at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:542) at org.springframework.beans.factory.support.AbstractBeanFactory.lambda$doGetBean$0(AbstractBeanFactory.java:335) at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:234) at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:333) at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:208) at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:322) at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:208) at org.springframework.beans.factory.config.DependencyDescriptor.resolveCandidate(DependencyDescriptor.java:276) at org.springframework.beans.factory.support.DefaultListableBeanFactory.doResolveDependency(DefaultListableBeanFactory.java:1391) at org.springframework.beans.factory.support.DefaultListableBeanFactory.resolveDependency(DefaultListableBeanFactory.java:1311) at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.autowireByType(AbstractAutowireCapableBeanFactory.java:1519) ... 51 common frames omitted Caused by: org.springframework.beans.BeanInstantiationException: Failed to instantiate [org.springframework.boot.autoconfigure.quartz.QuartzDataSourceScriptDataba seInitializer]: Factory method 'quartzDataSourceScriptDatabaseInitializer' threw exception; nested exception is java.lang.IllegalStateException: Unable to detect database type at org.springframework.beans.factory.support.SimpleInstantiationStrategy.instantiate(SimpleInstantiationStrategy.java:185) at org.springframework.beans.factory.support.ConstructorResolver.instantiate(ConstructorResolver.java:648) ... 66 common frames omitted Caused by: java.lang.IllegalStateException: Unable to detect database type at org.springframework.util.Assert.state(Assert.java:76) at org.springframework.boot.jdbc.init.PlatformPlaceholderDatabaseDriverResolver.determinePlatform(PlatformPlaceholderDatabaseDriverResolver.java:133) at org.springframework.boot.jdbc.init.PlatformPlaceholderDatabaseDriverResolver.lambda$resolveAll$0(PlatformPlaceholderDatabaseDriverResolver.java:97) at org.springframework.boot.jdbc.init.PlatformPlaceholderDatabaseDriverResolver.resolveAll(PlatformPlaceholderDatabaseDriverResolver.java:122) at org.springframework.boot.jdbc.init.PlatformPlaceholderDatabaseDriverResolver.resolveAll(PlatformPlaceholderDatabaseDriverResolver.java:97) at org.springframework.boot.autoconfigure.quartz.QuartzDataSourceScriptDatabaseInitializer.resolveSchemaLocations(QuartzDataSourceScriptDatabaseInitializer.java:105) at org.springframework.boot.autoconfigure.quartz.QuartzDataSourceScriptDatabaseInitializer.getSettings(QuartzDataSourceScriptDatabaseInitializer.java:89) at org.springframework.boot.autoconfigure.quartz.QuartzDataSourceScriptDatabaseInitializer.<init>(QuartzDataSourceScriptDatabaseInitializer.java:51) at org.springframework.boot.autoconfigure.quartz.QuartzAutoConfiguration$JdbcStoreTypeConfiguration.quartzDataSourceScriptDatabaseInitializer(QuartzAutoConfiguration.java:143) at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method) at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:77) at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43) at java.base/java.lang.reflect.Method.invoke(Method.java:568) at org.springframework.beans.factory.support.SimpleInstantiationStrategy.instantiate(SimpleInstantiationStrategy.java:154) ... 67 common frames omitted
最新发布
07-07
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值