从工厂模式理解Spring中BeanFactory

工厂方法模式是创建型设计模式,用于实例化对象,常与静态工厂结合使用以减少if-else。Spring的BeanFactory接口是工厂方法的一个应用,它通过反射动态创建bean并管理其生命周期,包括单例、多例、懒加载以及初始化和销毁方法。此外,BeanFactory还支持通过scope属性定义bean的实例化策略。
摘要由CSDN通过智能技术生成

工厂方法模式

工厂方法模式是一种实例化对象的模式,属于创建型模式,一般又可以分为简单工厂模式、工厂模式、抽象工厂模式,一般对于需要生成复杂对象的场景中,我们就可以使用工厂方法模式。

实际常用方法

在大多数情况下,我们一般不会像经典实现方式那样去做,而是结合静态方法那样,比如类似下面的这些方法:
在这里插入图片描述
在这里插入图片描述

看上去是不是也很像是单例模式,没错,实际上可以把两种模式结合一下。

public class InstanceFactory {

    private static final Map<String, FruitFactory> FRUIT_FACTORY_MAP = new HashMap<>();

    static {
        FRUIT_FACTORY_MAP.put("APPLE", new AppleFactory());
        FRUIT_FACTORY_MAP.put("BANANA", new BananaFactory());
    }

    public static Fruit newInstance(String name) {
        return FRUIT_FACTORY_MAP.get(name).newInstance();
    }

}
public class Test {
    public static void main(String[] args) {
        Fruit apple = InstanceFactory.newInstance("APPLE");

        Fruit banana = InstanceFactory.newInstance("BANANA");
    }
}

这样可以减少直接使用工厂模式时存在大量的if else的问题,只不过一般name传的都是class全限定名,然后通过反射的方式获取对象实例。

BeanFactory

Spring中的BeanFactory接口,定义的主要方法就是getBean,顾名思义就是专门用来获取bean对象的方法,那当然也可以看作是一种工厂方法,并且可以通过反射的机制,动态地加载类,从而让所有bean对象只需通过一个BeanFactory工厂就可以完成对象的创建。

public interface BeanFactory {

	String FACTORY_BEAN_PREFIX = "&";

	Object getBean(String name) throws BeansException;

	<T> T getBean(String name, Class<T> requiredType) throws BeansException;

	Object getBean(String name, Object... args) throws BeansException;

	<T> T getBean(Class<T> requiredType) throws BeansException;

	<T> T getBean(Class<T> requiredType, Object... args) throws BeansException;

	<T> ObjectProvider<T> getBeanProvider(Class<T> requiredType);

	<T> ObjectProvider<T> getBeanProvider(ResolvableType requiredType);

	boolean containsBean(String name);

	boolean isSingleton(String name) throws NoSuchBeanDefinitionException;

	boolean isPrototype(String name) throws NoSuchBeanDefinitionException;

	boolean isTypeMatch(String name, ResolvableType typeToMatch) throws NoSuchBeanDefinitionException;
	
	boolean isTypeMatch(String name, Class<?> typeToMatch) throws NoSuchBeanDefinitionException;

	@Nullable
	Class<?> getType(String name) throws NoSuchBeanDefinitionException;

	String[] getAliases(String name);

}

当然除了最常用的getBean方法之外,还有像isSingleton、isPrototype等方法,实际上也是我们在创建对象时需要考虑到的一些因素。

单例、多例

对于工厂方法,我们需要确定创建出来的bean是单例还是多例,Spring框架中,就为我们提供scope属性,用来定义单例或者多例对象。

在这里插入图片描述
在这里插入图片描述

是否懒加载

就像单例对象的懒汉、饿汉模式一样,对象的加载时机有时候也是需要我们考虑的,因为spring的bean工厂也为我们提供了这个属性的配置。

在这里插入图片描述
可以看到,只有非抽象的 && 单例的 && 非懒加载的,才会在spring容器初始化时,通过getBean方法进行bean对象的创建,否则则是等到真正调用时才会创建。

init-method 、 destroy-method

Spring框架优秀之处就在于,提供了各种各样的扩展点,在创建bean对象的时候,你还可以通过init-method方法自定义对象的初始化方法,也可以通过destroy-method方法自定对象的销毁过程。

在这里插入图片描述

总结

工厂方法虽然看起来很简单,但是要真正的考虑完善,实际上并没有那么简单,通过了解Spring中的BeanFactory,我们学习到了,首先可以利用反射机制,解决工厂方法中存在大量工厂类的问题,并且在创建bean对象时,还需要考虑对象是单例的还是多例的,是否需要懒加载,以及是否需要支持一些额外的初始化方法。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

码拉松

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值