Bean 的实例化(创建 | 获取)

  • Spring为Bean提供了多种实例化方式,包括如下4种方式:
    • 第一种:通过构造方法实例化
    • 第二种:通过简单工厂模式实例化
    • 第三种:通过factory-bean实例化(工厂方法模式实例化)
    • 第四种:通过FactoryBean接口实例化
  • Spring中为Bean对象的创建准备了多种方案,目的是为了能够更加灵活

通过构造方法实例化

  • 我们之前一直使用的就是这种方式。
  • 在spring配置文件中直接配置类全路径,即在Spring配置文件中配置bean,Spring会自动调用该类的无参数构造方法来实例化Bean

public class SpringBean {}

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd"><bean id="springBean" class="cw.spring.study.bean.SpringBean"/></beans>

通过简单工厂模式实例化

抽象产品类

public abstract class Fruit {}

具体产品类

public class Apple extends Fruit{}

工厂类
public class FruitFactory {// 创建水果对象的方法public static Fruit getFruit() {// 最终的Apple类对象是通过调用该工厂类的该方法new的对象return new Apple();}
}
配置文件配置工厂类生产 bean
  • 在Spring配置文件中告诉Spring框架,调用哪个类的哪个方法获取 Bean
<!--factory-method属性指定的是工厂类当中的静态方法,也就是告诉Spring框架,调用这个方法可以获取Bean创建出来的为产品对象,不为工厂对象,工厂类中的方法为静态方法,通过类名直接调用创建对象通过class属性指定的类调用该类的静态工厂方法,进行对象的创建,最终创建的对象为产品对象,id为apple
-->
<bean id="apple" class="cw.spring.study.bean.FruitFactory" factory-method="getFruit"/>
测试
@org.junit.Test
public void test1() {ApplicationContext applicationContext = new ClassPathXmlApplicationContext("spring.xml");System.out.println(applicationContext.getBean("apple", Fruit.class));
}

通过factory-bean实例化(工厂方法模式实例化)

抽象产品类
/*** ClassName: Fruit* Package: cw.spring.study.bean* Description:*/
public abstract class Fruit {}
具体产品类
/**
* ClassName: Apple
* Package: cw.spring.study.bean
* Description:
*/
public class Apple extends Fruit{}
抽象工厂类
/*** ClassName: FruitFactory* Package: cw.spring.study.bean* Description:*/
public abstract class FruitFactory {/*** 水果工厂生产水果的方法* * @return 水果*/public abstract Fruit getFruit();}
具体工厂类
/*** ClassName: AppleFactory* Package: cw.spring.study.bean* Description:** @Author tcw* @Create 2023-05-25 18:37* @Version 1.0*/
public class AppleFactory extends FruitFactory{// 实例方法@Overridepublic Fruit getFruit() {// 生产苹果return new Apple();}
}
配置文件配置工厂类生产 bean
  • 告诉Spring框架,调用哪个对象的哪个方法来获取Bean
<!-- 工厂方法模式,通过 factory-bean属性 + factory-method属性来共同完成 由于工厂类用于创建对象的方法为实例方法,所以需要先创建工厂对象,工厂对象也需要被spring管理AppleFactory 实际上是一个工厂bean,用于创建对象的bean
-->
<bean id="appleFactory" class="cw.spring.study.bean.AppleFactory"/>
<!--factory-bean属性告诉Spring调用哪个工厂对象,进行bean的创建factory-method属性告诉Spring调用工厂对象的哪个实例方法创建bean该配置用于指定用哪个工厂对象的哪个方法创建对象
-->
<bean id="apple" factory-bean="appleFactory" factory-method="getFruit"/>
测试
@org.junit.Test
public void test1() {ApplicationContext applicationContext = new ClassPathXmlApplicationContext("spring.xml");System.out.println(applicationContext.getBean("apple", Fruit.class));
}

通过FactoryBean接口实例化

  • 以上的第三种方式中,factory-bean(生产bean的工厂bean)是我们自定义的,factory-method(生产bean的工厂方法)也是我们自己定义的。
  • 在Spring中,当我们编写的类直接实现FactoryBean接口之后,用于创建bean的factory-bean就不需要我们指定了,工厂bean的factory-method也不需要我们指定了。factory-bean会自动指向实现FactoryBean接口的类,factory-method会自动指向该类中的getObject()方法。
    • 因为我们在配置文件中指定的用于创建bean的类在实现FactoryBean接口之后,Spring就知道这是一个工厂类,并且知道工厂方法是哪个
  • 这种方式实际上就是第三种方式的简化
  • FactoryBean在Spring中是一个接口,被称为“工厂Bean”。
  • “工厂Bean”是一种特殊的Bean,所有的“工厂Bean”都是用来协助Spring框架来创建其他Bean对象的。
产品类
/*** ClassName: Person* Package: cw.spring.study.bean* Description:** @Author tcw* @Create 2023-05-25 18:56* @Version 1.0*/
public class Person {}
工厂类
import org.springframework.beans.factory.FactoryBean;/*** ClassName: PersonFactoryBean* Package: cw.spring.study.bean* Description:** @Author tcw* @Create 2023-05-25 18:57* @Version 1.0*/
public class PersonFactoryBean implements FactoryBean<Person> {// 创建bean的工厂方法@Overridepublic Person getObject() throws Exception {return new Person();}@Overridepublic Class<?> getObjectType() {return null;}
}
public interface FactoryBean<T> {String OBJECT_TYPE_ATTRIBUTE = "factoryBeanObjectType";@NullableT getObject() throws Exception;@NullableClass<?> getObjectType();// 该方法接口进行了默认实现,工厂bean创建的对象是否为单例的// 默认情况下,创建的对象是单例的// 如果要让工厂bean创建的对象为多例,则重写该方法,返回false即可default boolean isSingleton() {return true;}
}
配置文件配置工厂类生产 bean
<!--这种方式实际上就是第三种方式的简化。由于你编写的类实现了FactoryBean接口,所以这个类是一个特殊的类,不需要你再手动指定:factory-bean、factory-method实现了FactoryBean接口,Spring知道这是一个工厂类,并且知道用于创建bean的工厂方法是哪个通过一个特殊的Bean:工厂Bean,来返回一个普通的Bean Person对象。通过FactoryBean这个工厂Bean主要是想对普通Bean进行加工处理。
-->
<bean id="person" class="cw.spring.study.bean.PersonFactoryBean"/>
测试
@org.junit.Test
public void test1() {ApplicationContext applicationContext = new ClassPathXmlApplicationContext("spring.xml");System.out.println(applicationContext.getBean("person", Person.class));
}

工厂方法实例化小结

相比于通过构造方法进行bean的实例化,采用工厂方法进行bean的实例,我们可以在bean对象创建出来到将创建出来的对象交给Spring容器进行管理这一段时间内,我们可以对bean对象进行加工处理。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/web/51802.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

盘点java8 stream中隐藏的函数式接口

shigen坚持更新文章的博客写手&#xff0c;记录成长&#xff0c;分享认知&#xff0c;留住感动。个人IP&#xff1a;shigen 提到函数式接口&#xff0c;最常见的就是lambda表达式&#xff0c;IDEA也有智能的提示&#xff1a; 最后改成这样的就是最简洁的、IDEA希望的风格&#…

Android UI绘制原理:UI的绘制流程是怎么样呢?为什么子线程不能刷新UI呢?讲解大体的流程是怎么样的

目录&#xff1a; 一、 为什么要学习android UI绘制原理呢&#xff1f;对我们有什么帮助&#xff1f; 1.解决复杂布局问题&#xff1a;了解UI绘制原理可以帮助我们更好地理解和解决布局问题&#xff0c;比如使用自定义View、优化布局层级等。 2.知道何时触发布局&#xff08;…

Java中的阻塞队列BlockingQueue

阻塞队列简介 阻塞队列是一个支持两个附加操作的队列 -> 支持阻塞的插入方法&#xff1a;当队列满时&#xff0c;队列会阻塞插入元素的线程&#xff0c;直到队列不满支持阻塞的移除方法&#xff1a;意思是在队列为空时&#xff0c;获取元素的线程会等待队列为非空 ->这…

【AI大模型】基于docker部署向量数据库Milvus和可视化工具Attu详解步骤

&#x1f680; 作者 &#xff1a;“大数据小禅” &#x1f680; 文章简介 &#xff1a;本专栏后续将持续更新大模型相关文章&#xff0c;从开发到微调到应用&#xff0c;需要下载好的模型包可私。 &#x1f680; 欢迎小伙伴们 点赞&#x1f44d;、收藏⭐、留言&#x1f4ac; 目…

zdppy_cache缓存框架升级,支持用户级别的缓存隔离,支持超级管理员管理普通用户的缓存

启动服务 import zdppy_api as api import zdppy_cachekey1 "admin" key2 "admin"app api.Api(routes[*zdppy_cache.zdppy_api.cache(key1, key2, api) ])if __name__ __main__:import zdppy_uvicornzdppy_uvicorn.run(app, host"0.0.0.0",…

TEngine框架之HybridCLR代码热更

自HybridCLR热更方案出现以来&#xff0c;像之前的主流toLua/xLua/ILRuntime瞬间不香了&#xff0c;算是跨世代的产物引起业界不小的轰动。HybridCLR是一个特性完整、零成本、高性能、低内存的近乎完美的Unity全平台原生c#热更新解决方案。想要详细了解HibirdCLR原理和使用的&a…

初爽Stream流

体验Stream流的作用&#xff1a; 需求&#xff1a; 按照下面的要求完成集合的创建和遍历 创建一个集合&#xff0c;存储多个字符串元素 要求&#xff1a; 1.把所有以“张”开头的元素存储到新集合中 2.把“张”开头的&#xff0c;长度为3的元素再存储到新集合中 3.遍历打…

【C++ | 设计模式】代理模式的详解与实现

1. 概念 代理模式&#xff08;Proxy Pattern&#xff09;是一种结构型设计模式&#xff0c;用于控制对对象的访问。它通过引入代理对象&#xff0c;间接地操作目标对象&#xff0c;从而实现对目标对象的控制。代理模式的核心思想是通过代理对象来控制对目标对象的访问。代理对…

kubenetes--资源调度

前言&#xff1a;本博客仅作记录学习使用&#xff0c;部分图片出自网络&#xff0c;如有侵犯您的权益&#xff0c;请联系删除 出自B站博主教程笔记&#xff1a; 完整版Kubernetes&#xff08;K8S&#xff09;全套入门微服务实战项目&#xff0c;带你一站式深入掌握K8S核心能…

Python-FLASK上传文件

一、HTML文件 1、avator.html <!DOCTYPE html> <html lang"en"> <head><meta charset"UTF-8"><title>Title</title> </head> <body> <form method"post" enctype"multipart/form-dat…

【Python】如何使用pip,安装第三方库和生成二维码、操作Excel

文章目录 第三方库使用 pip安装第三方库 生成二维码1. 确定使用哪个库2. 查看对应文档3. 开始操作 操作 Excel1. 安装 xlrd2. 编写代码 第三方库 第三方库就是别人已经实现好了的库&#xff0c;我们可以拿过来直接使用 虽然标准库已经很强大了&#xff0c;但是终究是有限的&am…

英语写作中“详述”expand on/upon的用法

“详述”的简单表达是explain ……in detail 或describe……in detail等。 &#xff08;见&#xff1a;【英语写作中用“解释”explain、elucidate、articulate、explicate 替代“描述”describe - CSDN App】&#xff09; expand on/upon是“详述”的另一表达&#xff0c;在需…

MLM之Qwen:Qwen2-VL的简介、安装和使用方法、案例应用之详细攻略

MLM之Qwen&#xff1a;Qwen2-VL的简介、安装和使用方法、案例应用之详细攻略 目录 Qwen2-VL的简介 1、主要增强功能&#xff1a; 2、模型架构更新&#xff1a; 3、性能 图像基准测试 视频基准测试 代理基准测试 多语言基准测试 4、新闻 5、限制 Qwen2-VL的安装和使用…

微服务间调用

一、restTemplate 1、先将restTemplate注册成为一个bean Configuration public class RemoteCallConfig {Beanpublic RestTemplate restTemplate() {return new RestTemplate();} }2、实现代码 private void handleCartItems(List<CartVO> vos) {// TODO 1.获取商品id…

python requests 常用小工具,代码片,速查,整理

起因(目的): 爬虫其实是很零碎的事情。 小工具&#xff0c; 就像是小螺丝一样&#xff0c; 有空整理一下工具箱。 过程: 自定义请求头&#xff0c;将 Accept-Language 设置为美国的英语。 尤其爬国外的网站&#xff0c; 不然会出现很奇怪的中文。 headers {# 将 Accept-La…

Nginx使用alias代理PHP项目提示FastCGI sent in stderr: “Primary script unknown“ 问题完美解决

踩坑记录 为了方便运营推广,我们有一个需求就是用一个域名达到访问两个PHP项目的目的,本来想着这很简单,就是一个代理解决问题,于是便非常潇洒的分分钟配置了一下,如下: server {listen 80;server_name ab.com;index index.html index.htm index.php index.shtml;root /…

【网络安全】服务基础第一阶段——第八节:Windows系统管理基础---- Web服务与虚拟主机

目录 一、WWW概述 1.1 HTML 1.2 URI与URL 1.2.1 URL&#xff08;统一资源标识符&#xff0c;Uniform Resource Locator&#xff09; 1.3 HTTP 1.3.1 HTTP请求&#xff1a; 1.3.2 HTTP响应 1.3.3 状态码 1.4常见Web URL格式 实验一、网站搭建 1&#xff09;访问失败可…

如何基于numpy和scipy实现曲面的最大梯度计算与显示

大家在做三维可视化研究过程中,经常需要做三维曲面的绘制和相交分析,在不知道三维曲面方程的情况下,如何基于曲面散点数据计算曲面的最大梯度点和梯度线的三维可视化是大家基于曲面分析研究中的重点关注的问题,本文在python环境下,基于numpy、pandas、scipy和matplotlib等…

超详细Git基本命令使用(二)

&#x1f600;前言 本篇博文是关于 Git基本命令的使用&#xff0c;希望你能够喜欢 &#x1f3e0;个人主页&#xff1a;晨犀主页 &#x1f9d1;个人简介&#xff1a;大家好&#xff0c;我是晨犀&#xff0c;希望我的文章可以帮助到大家&#xff0c;您的满意是我的动力&#x1f6…

【C++】list的使用和list的模拟实现和迭代器失效问题

目录 一、list 的简单介绍 二、list 的基本使用 &#x1f389;list的构造 &#x1f389;list iterator 的使用 &#x1f389;list capacity &#x1f389;list element access &#x1f389;list modifiers &#x1f389;list operator 三、list 的模拟实现 &#x…