Spring框架之DI依赖注入

news2024/9/21 23:28:51

        Di(Dependence Injection)依赖注入,在spring框架负责创建bean对象时,动态地将依赖对象注入到其它对象中

一、什么是依赖注入。

我们在下面构建spring的过程中体会依赖注入; 

        从上面的图中我们知道,在ssm框架中服务层(server)无法直接操作数据库,持久层(dao)是直接操作数据库进行数据处理的,但是我们如果在服务层有一个持久层的对象,然后我们在服务层通过对象去调用持久层的方法就可以操作数据库了。

package com.exam.dao;

public interface UserDao {
    void hello();
}
package com.exam.dao.Impl;

import com.exam.dao.UserDao;

public class UserDaoImpl implements UserDao {
    @Override
    public void hello() {
        System.out.println("持久层,你好");
    }
}


UserServiceImpl类中的代码如下

package com.exam.service.impl;

import com.exam.dao.UserDao;
import com.exam.service.UserService;

public class UserServiceImpl implements UserService {
    private UserDao userDao;
    @Override
    public void hello(){
        userDao.hello();
    }
}

这就是通过服务层去访问持久层的方法,我们在UserServiceImpl中定义了一个持久层(dao层)的对象UserDao,不过目前userDao对象还没有赋值,我们能想到的赋值方法应该只有使用new关键字。

private UserDao userDao = new UserDao()

 而Di依赖注入就是使用Spring配置文件来完成赋值这一步(可以把依赖注入就理解为给属性赋值),这样代码维护起来会更加方便

二、依赖注入的方式

1.属性的set方法注入值的方式

我们需要在server层类中写一个set方法,如下

在UserServerImpl类中添加set方法

    public void setUserDao(UserDao userDao) {
        this.userDao = userDao;
    }

现在我们对xml文件进行配置

    <bean id="us" class="com.exam.service.impl.UserServiceImpl">
        <property name="userDao" value=""/>
    </bean>

如果是要对某个类的对象进行管理使用的是<bean>,如果要对某个类中的对象进行管理,我们使用的就是<property>,这个过程就叫做依赖注入(Di),底层也是通过反射实现的

<property name="userDao" ref=""/>
<property name="age" value=""/>

在这个标签中,name的值代表了对象的属性名,ref和value都是给属性赋值,那么这两个的区别是什么呢?

ref和value的区别

如果是简单类型(基本类型+字符串)property标签使用value

如果是自定义引用类型, property标签使用ref

那么我们该怎么给ref和value赋值呢?

        为了方便演示我们在UserServerImpl中添加了age属性和对应的set方法,下面是使用ref和value的应用情况。

    <bean id="us" class="com.exam.service.impl.UserServiceImpl">
        <property name="userDao" ref="ud"/>
        <property name="age" value="18"/>
    </bean>
    <bean id="ud" class="com.exam.dao.Impl.UserDaoImpl"/>

我们分别在配置了依赖注入未配置依赖注入的情况下执行test代码

    @Test
    public void run2(){
        //创建spring ioc工厂,目的是加载spring配置文件
        ApplicationContext ac = new ClassPathXmlApplicationContext("applicationContext.xml");
        //创建bean对象
        UserService userService = (UserService) ac.getBean("us");
        userService.hello();
    }

没配置的情况

报错了显示空指针 


配置了的情况

 

在依赖注入的情况下,我们想更改一个对象的值只需要更改配置文件就可以,不需要去找修改源代码,例如将年龄改成30,只需要更改,下面代码即可,维护起来更加方便。

        <property name="age" value="18"/>

2.构造方法注入值的方法

首先在UserServerImpl中添加构造方法,记得还得写无参构造方法,不然IOC  bean对象管理的时候会报错

    public UserServiceImpl(UserDao userDao, int age) {
        this.userDao = userDao;
        this.age = age;
    }
    <bean id="us" class="com.exam.service.impl.UserServiceImpl">
        <constructor-arg name="age" value="18"/>
        <constructor-arg name="userDao" ref="ud"></constructor-arg>
    </bean>
    <bean id="ud" class="com.exam.dao.Impl.UserDaoImpl"/>

<constructor-arg>标签的name属性值,必须完全和构造方法中的形参对应,不能多不能少,比如构造方法中有name,那么<bean>标签中就不能只写

<constructor-arg name="userDao" ref="ud"></constructor-arg>

 那么我们怎么通过依赖注入去给数组这种集合类的数据赋值呢?

1.不可变数组赋值

例如在CollectionNean类中

public class CollectionNean {
    private String[] str;

    public void setStr(String[] str) {
        this.str = str;
    }
}

我们的配置文件就应该这么写

    <bean id="co" class="com.exam.service.impl.CollectionNean">
        <property name="str">
            <array>
                <value>张三</value>
                <value>小妹</value>
                <value>小红</value>
            </array>
        </property>
    </bean>
    @Test
    public void run2(){
        //创建spring ioc工厂,目的是加载spring配置文件
        ApplicationContext ac = new ClassPathXmlApplicationContext("applicationContext.xml");
        //创建bean对象
        CollectionNean collectionNean = (CollectionNean) ac.getBean("co");
        System.out.println(collectionNean.toString());
    }

2.可变数组是怎么注入值的呢

这里指的是Java中的LIst<>类型

    private List<String> list;
    public void setList(List<String> list) {
        this.list = list;
    }
        <property name="list">
            <list>
                <value>熊大</value>
                <value>熊二</value>
            </list>
        </property>

 3.给map类型注入值

    private Map<String,String> map;
    public void setMap(Map<String, String> map) {
        this.map = map;
    }
        <property name="map">
            <map>
                <entry key="name" value="张三"></entry>
                <entry key="age" value="31"></entry>
                <entry key="sex" value="男"></entry>
            </map>
        </property>

4.给properties类型注入值

    private Properties properties;

    public void setProperties(Properties properties) {
        this.properties = properties;
    }
        <property name="properties">
            <props>
                <prop key="username">root</prop>
                <prop key="password">123456</prop>
            </props>
        </property>

三、多配置文件的加载方式:

1.在主配置文件中使用import

    <import resource="applicationContext2.xml"/>
ApplicationContext ac = new ClassPathXmlApplicationContext("applicationContext.xml");

2.在创建工厂时直接加载多个配置文件

ApplicationContext ac = new ClassPathXmlApplicationContext("applicationContext.xml","applicationContext.xml2");

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

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

相关文章

【操作系统】文件管理——文件共享与保护,文件系统的结构(个人笔记)

学习日期&#xff1a;2024.7.18 内容摘要&#xff1a;文件共享&#xff0c;文件保护&#xff0c;文件系统的层级结构和全局结构&#xff0c;虚拟文件系统 文件共享 操作系统提供的文件共享功能&#xff0c;可以让多个用户共享使用同一个文件。文件共享和文件复制是不一样的&a…

DP(6) | 完全背包 | Java | LeetCode 322, 179, 139 做题总结

322. 零钱兑换 我的错误答案 class Solution {public int coinChange(int[] coins, int amount) {int[][]dp new int [coins.length][amount1];for(int j0; j<amount; j) {if(coins[0] j){dp[0][coins[0]] 1;}}for(int i1; i<coins.length; i) {for(int j0; j<am…

实战篇(十一) : 拥抱交互的三维世界:利用 Processing 和 OpenGL 实现炫彩粒子系统

🌌 拥抱交互的三维世界:利用 Processing 和 OpenGL 实现炫彩粒子系统 在现代计算机图形学中,三维粒子系统是一个激动人心的领域。它不仅可以用来模拟自然现象,如烟雾、火焰和水流,还可以用来创造出令人叹为观止的视觉效果。在这篇文章中,我们将深入探讨如何使用 Proces…

Dify中的高质量索引模式实现过程

思考在什么情况下会使用到高质量索引模式呢?第1种情况是在知识库中上传文档,文档被拆分为段落后需要进行编码(增加);第2种情况是在召回测试的时候,需要对query进行编码(查询);第3种情况是当文档中的段落增加和更新时需要进行编码(增加和更新)。索引模式是针对知识库…

springboot 配置 spring data redis

1、在pom.xml引入父依赖spring-boot-starter-parent&#xff0c;其中2.7.18是最后一版支持java8的spring <parent><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-parent</artifactId><version>2.7.18</…

汇编教程2

本教程主要教大家如何安装32位Linux虚拟机&#xff0c;为后续实验拆炸弹做准备 下载系统映像文件 以Ubuntu14.04.6系统为例 官方网站&#xff1a;下载地址 点击下载图中32位系统 如果官网进不去可以使用镜像网站 清华镜像网站&#xff1a;下载地址 进入之后找到下图中链接…

如何在项目中使用线程池自定义拒绝策略

首先呢&#xff0c;我设计了一个图表在我的项目里面&#xff0c;为了方便展示&#xff0c;我只修改一个字段&#xff0c;线程池设置参数 (2,4,30, TimeUnit.SECONDS, new ArrayBlockingQueue<>(4),new RJ()); 然后通过循环持续的进行增加任务&#xff0c;目的修改数据库的…

解决element-ui e-table表格中使用多选,当翻页时已选中的数据丢失

用element-ui中的table时&#xff0c;当有多选又有翻页功能时&#xff0c;点击翻页后之前选中的数据会丢失&#xff0c;怎么使表格具有记忆功能呢 element-ui API中有几个属性可以供我们完美解决这个问题 1.单元格的属性和方法&#xff1a; 2.表格的方法&#xff1a; <el-…

微软成为PostgreSQL主要贡献者

微软对PostgreSQL贡献的很多新功能都来自于客户在使用微软Azure上的PostgreSQL管理实例数据库&#xff0c;所以这些新功能都来自于真实的客户需求 微软贡献的这些新功能都是比较实用的功能 在这里&#xff0c;【真实的客户需求】要突出一下&#xff0c;因为现在很多社区贡献者…

什么是正则表达式,如何在 Python 中使用?

什么是正则表达式 正则表达式&#xff08;Regular Expression&#xff0c;简称Regex&#xff09;是一种用于匹配字符串中字符模式的工具。它是由普通字符&#xff08;例如字母、数字&#xff09;以及一些特殊字符&#xff08;称为元字符&#xff09;组成的字符序列。这种模式用…

【SASS/SCSS(三)】样式的复用与动态计算(@mixin和@function)

目录 一、mixin 1、定义复用的样式代码&#xff0c;接受传参&#xff0c;搭配include使用。 位置传参 关键词传参 ...语法糖接受传入的任意参数 2、在mixin中使用content&#xff0c;获取外部对mixin的追加内容 二、function 三、字符串——值得注意的点 很多时候&#…

云微客如何实现低成本快速获客?AI矩阵来传播

目前市场环境较为严峻&#xff0c;超过上千万家实体商家都会遇到线下获客难、线上营销成本高的困境&#xff0c;因此商家急需新的获客方案。 云微客AI矩阵系统基于AIGC的企业短视频矩阵及内容生成、协作、管理平台&#xff0c;通过对多个短视频平台进行营销覆盖&#xff0c;深入…

【机器学习】--下采样原理及代码详解

下采样&#xff08;Downsampling&#xff09;是信号处理、图像处理和机器学习中的一个关键概念&#xff0c;主要通过减少数据点的数量来降低信号或图像的采样率 一、定义与原理 定义&#xff1a;下采样是指通过减少数据点的数量来降低信号或图像的采样率。在图像处理中&#…

vue使用x6画流程图,简单使用

官网 https://x6.antv.antgroup.com/tutorial/getting-started 安装 npm install antv/x6 --save 使用 <template><div>3333<div id"container" style"width: 800px;height: 800px;"></div></div> </template> <…

无人机之多旋翼与固定翼的区别

多旋翼无人机和固定翼无人机是无人机技术中的两种主要形式&#xff0c;各自有独特的优势和应用场景。 一、飞行原理与结构 多旋翼无人机&#xff1a;依靠多个旋翼产生升力来平衡飞行器的重力&#xff0c;通过改变每个旋翼的转速控制飞行器的姿态和平稳&#xff0c;使其能够垂…

Linux-开机自动挂载(文件系统、交换空间)

准备磁盘 添加三块磁盘&#xff08;两块SATA&#xff0c;一块NVMe&#xff09; 查看设备&#xff1a; [rootlocalhost jian]# ll /dev/sd* [rootlocalhost jian]# ll /dev/nvme0n2 扩&#xff1a;查看当前主机上的所有块设备&#xff0c;通过如下指令实现&#xff1a; [root…

云监控(华为) | 实训学习day2(10)

spring boot基于框架的实现 简单应用 - 用户数据显示 开发步骤 第一步&#xff1a;文件-----》新建---项目 第二步:弹出的对话框中,左侧选择maven,右侧不选任何内容. 第三步&#xff0c;选择maven后&#xff0c;下一步 第4步 &#xff1a;出现对话框中填写项目名称 第5步&…

json将列表字典等转字符串,然后解析又转回来

在 Python 中使用 json 模块来方便地在数据和 JSON 格式字符串之间进行转换&#xff0c;以便进行数据的存储、传输或与其他支持 JSON 格式的系统进行交互。 JSON 字符串通过 json.loads() 函数转换为 Python 对象。 pthon对象通过json.dumps()转为字符串 import jsonstr_list…

StarRocks on AWS Graviton3,实现 50% 以上性价比提升

在数据时代&#xff0c;企业拥有前所未有的大量数据资产&#xff0c;但如何从海量数据中发掘价值成为挑战。数据分析凭借强大的分析能力&#xff0c;可从不同维度挖掘数据中蕴含的见解和规律&#xff0c;为企业战略决策提供依据。数据分析在营销、风险管控、产品优化等领域发挥…

PostgreSQL的逻辑架构

一、PostgreSql的逻辑架构&#xff1a; 一个server可以有多个database&#xff1b;一个database有多个schema&#xff0c;默认的schema是public&#xff1b;schema下才是对象&#xff0c;其中对象包含&#xff1a;表、视图、触发器、索引等&#xff1b;与user之间的关系&#x…