Spring DI 简单演示三层架构——Setter 注入

news2024/9/22 8:24:26

Spring IOC 的常见注入方法有3种:Setter注入、构造注入属性注入。想了解更多可点击链接:Spring 注入、注解以及相关内容补充

        属性注入 不推荐。原因:使用私有的成员属性变量,依靠反射实现,破坏封装,只能依靠 IOC 容器实现注入,不严谨。所以我只演示Setter注入构造注入。本篇演示Setter注入

首先新建项目,可参考 初识IDEA、模拟三层--控制层、业务层和数据访问层

一、spring 环境搭建

(一)pom.xml 导相关坐标

<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0"
         xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
         xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
    <modelVersion>4.0.0</modelVersion>
<!--    导坐标,不导入该坐标会影响xml文件创建
导完坐标,一定去该页面右边点开 Maven看看是否下载完成,
若不报错,即下载成功-->
    <dependencies>
        <dependency>
            <groupId>org.springframework</groupId>
            <artifactId>spring-context</artifactId>
            <version>5.3.28</version>
        </dependency>
    </dependencies>

    <groupId>org.example</groupId>
    <artifactId>Spring_ioc_04</artifactId>
    <version>1.0-SNAPSHOT</version>


</project>

(二)搭建配置文件

依次点击:src ==> main ==> resource 右击  ==> New ==> 找 XML Configuration File ==> 找到 Spring Config 并点击,起名(自己随便起名字),为了好区分,我起名叫 applicationContext

(三)建包建类,写方法

        建包建类,写方法可参考模拟三层--控制层、业务层和数据访问层,我们建立dao 包、 service 包、controller 包和 test 包。dao 包、 service 包和 controller 包这三个包分别写三层的接口和实现类,名字随便起的,习惯了“Student”,我给所有的名字都包含了“Student” ,其实“Student”没啥意义,“IUserDao"或”bsygd"这样随便的名字都行,什么的名字都一样的意义,取名自己好区分好记住就行(不过为了好区分,最好数据访问层、业务层、控制层起名都包含各自的dao 、service、controller字样,接口都 I 开头、实现类都 imp 结尾)。text 包就写测试类,因为本片文章简单演示而已,我们就简单的给每个接口写个 save() 新增方法给大家演示吧,具体代码如下:

//dao 数据访问层的接口
package com.apesource.pojo.dao;

public interface IStudentDao {
    public void save();
}
//dao 数据访问层的实现类
package com.apesource.pojo.dao;

public class StudentDaoImp implements IStudentDao{
    @Override
    public void save() {
        System.out.println("===dao的新增方法===");
    }
}
//service 业务层接口
package com.apesource.pojo.service;

public interface IStudentService {
    public void save();
}
//service 业务层实现类
package com.apesource.pojo.service;

import com.apesource.pojo.dao.IStudentDao;

public class StudentServiceImp implements IStudentService{
    /*因为 service 层调用数据访问层
     *我们得将 dao 层与 service 联系起来
     *拿到一个 实现dao层方法的变量,又由于我们要使用 setter 方法注入
     * 所以我们要写它的 setter 方法*/
    IStudentDao dao;
    public void setDao(IStudentDao dao) {
        this.dao = dao;
    }

    @Override
    public void save() {
        System.out.println("===service的新增方法===");
        //调用 dao 层方法
        dao.save();
    }
}
//controller 控制层接口
package com.apesource.pojo.controller;

public interface IStudentController {
    public void save();
}
//controller 控制层的实现类
package com.apesource.pojo.controller;

import com.apesource.pojo.dao.IStudentDao;
import com.apesource.pojo.service.IStudentService;

public class StudentControllerImp implements IStudentController{
    /*因为 controller 层调用数据访问层
     *我们得将 controller 层与 service 联系起来
     *拿到一个实现 service 层方法的变量,又由于我们要使用 setter 方法注入
     * 所以我们要写它的 setter 方法*/
    IStudentService service;
    public void setService(IStudentService service) {
        this.service = service;
    }

    @Override
    public void save() {
        System.out.println("===contro的新增方法===");
        //调用 service 层方法
        service.save();
    }
}

(四)找到需要以解耦方式获取实例的类,将需要spring管理的类注入,通过 application.xml 配置文件的操作

<?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">
    <!--注入数据访问——dao实现类-->
    <!--<bean id="可以自己起名,先写 class,再写 id,系统会自动生成 id 名,很方便" class="实现类或需要解耦的类的路径"></bean>-->
    <bean id="daoImp" class="com.apesource.dao.StudentDaoImp"></bean>

    <!--注入业务——service实现类-->
        <!--业务层需要数据访问层层对象注入,DI实现,子标签-->
        <!--property 子标签,就用于 setter 注入,它也会有自动生成的 name,可以改自己起的名,自动生成很方便-->
            <!--property的name指要通过 setter给注入的属性名-->
            <!--property的value指要通过 setter给注入的数据,写具体值-->
            <!--property的ref可以直接引用标签id-->
    <bean id="serviceImp" class="com.apesource.service.StudentServiceImp">
        <!--通过 setter给注入的dao(就我们service层添加的那个dao层的属性【IStudentDao dao】),ref可以直接引用数据访问层id,这样两层就关联起来了,控制层同理-->
        <property name="dao" ref="daoImp"></property>
    </bean>

    <!--注入控制器——controller实现类-->
        <!--控制层需要业务层对象注入,DI实现-->
    <bean id="controllerImp" class="com.apesource.controller.StudentControllerImp">
        <property name="service" ref="serviceImp"></property>
    </bean>
</beans>

(五)测试类

package com.apesource.test;

import com.apesource.controller.IStudentController;
import org.springframework.context.support.ClassPathXmlApplicationContext;
//注意:千万不要忘记 main 主方法
public class Test01 {
    public static void main(String[] args) {
        //1.加载 Spring 核心配置文件,获取 Spring 容器对象
        //applicationContext.xml为建完坐标下一步自己建立的那个 xml 配置文件的名字
        ClassPathXmlApplicationContext applicationContext = new ClassPathXmlApplicationContext("applicationContext.xml");
        //2.获取对象【.getBean("controllerImp")这个controllerImp是 xml 配置文件控制层标签的 id】
        IStudentController controllerImp = (IStudentController) applicationContext.getBean("controllerImp");
        controllerImp.save();//看它是否三层关联调用方法
    }
}

运行结果(控制层显示出数据访问层方法结果,三层关联成功):

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

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

相关文章

~Keepalived高可用集群~

一、Keepalived简介 是一个用于实现高可用性的解决方案&#xff0c;它主要应用于云主机的主备切换&#xff0c;以达到高可用性&#xff08;HA&#xff09;的目的。当主服务器发生故障无法对外提供服务时&#xff0c;动态将虚拟IP切换到备服务器&#xff0c;继续对外提供服务&a…

DOM破坏

XSS Game 1、第一关 Ma Spaghet! <!-- Challenge --> <h2 id"spaghet"></h2> <script>spaghet.innerHTML (new URL(location).searchParams.get(somebody) || "Somebody") " Toucha Ma Spaghet!" </script> S…

【ubuntu24.04】wget配置代理加速下载

参考之前的wget代理配置 wget速度非常慢 配置控制台代理不行 配置wget代理 本机部署了代理程序:all_proxy 不识别:root@PerfSvr:~# cat set65proxy.sh #!/bin/sh export

[STM32F429_硬件知识01]

知识点1 &#xff1a;J-Link的使用步骤&#xff1a; step1 : 安装J-Link驱动程序 step2 : keil的魔术棒中 -> Debug -> Use中选择J_Link ->点击 Settings ->

AI 时代风暴:程序员的核心竞争力大揭秘

引言&#xff1a; 在当今科技浪潮以排山倒海之势汹涌澎湃之际&#xff0c;人工智能宛如璀璨星辰般不断涌现&#xff0c;AIGC&#xff08;如 chatgpt、midjourney、claude 等&#xff09;大语言模型如雨后春笋般破土而出&#xff0c;AI 辅助编程工具更是以风驰电掣之速迅速席卷编…

智能电销机器人提升工作效率

随着科技的不断发展&#xff0c;电销行业也在不断探索创新&#xff0c;其中电销机器人作为一种高效的工具&#xff0c;正逐渐成为企业提升工作效率的利器。让我们一起看看电销机器人如何助力企业提高效率&#xff1a; 1. 自动化拨打电话 电销机器人每天可以自动拨打大量电话&a…

element-plus表格组件el-table 的使用

表格是在前端页面中是经常被用到的&#xff0c;尤其是管理系统&#xff0c;几乎每个页面都会存在表格&#xff0c;所以掌握表格组件是非常有必要的。element-plus提供el-table&#xff0c;el-table-column来渲染表格&#xff0c; 1. el-table 组件主要属性 属性名作用值类型…

【C语言小项目】五子棋游戏

目录 前言 一、游戏规则 1.功能分析 2.玩法分析 3.胜负判定条件 二、游戏实现思路 三、代码实现与函数封装 1.项目文件创建 2.头文件说明 3.函数封装 1&#xff09;菜单实现 2&#xff09;进度条实现 3&#xff09;main函数实现 4&#xff09;Game函数 5&#xff0…

Java语言程序设计——篇十三(4)

&#x1f33f;&#x1f33f;&#x1f33f;跟随博主脚步&#xff0c;从这里开始→博主主页&#x1f33f;&#x1f33f;&#x1f33f; 欢迎大家&#xff1a;这里是我的学习笔记、总结知识的地方&#xff0c;喜欢的话请三连&#xff0c;有问题可以私信&#x1f333;&#x1f333;&…

下载中心: 使用异步方法生成文件任务+键集分页查询

文章目录 引言I 下载中心功能进度表设计异步处理文件生成案例II 键集分页查询提高查询效率解决分页查询出现数据重复或丢失案例III 工具线程池基于EasyExcel 生成 excel文件存储系统see also引言 需求: 根据查询条件导出数据,比如交易流水、设备安装资料。 流程设计:点击导…

牛客面经学习笔记(二)

锂离子电池的充电过程可以分为四个阶段&#xff1a;涓流充电&#xff08;低压预充&#xff09;、恒流充电、恒压充电以及充电终止。 阶段1&#xff1a;涓流充电——涓流充电用来先对完全放电的电池单元进行预充(恢复性充电)。在电池电压低于3V左右时采用涓流充电&#xff0c;涓…

Vue 生命周期详解含demo、面试常问问题案例

Vue 生命周期详解、面试常问问题案例 含 demo 文章目录 Vue 生命周期详解、面试常问问题案例 含 demo一、Vue 生命周期是什么二、Vue 中如何使用生命周期钩子1. **beforeCreate**2. **created**3. **beforeMount**4. **mounted**5. **beforeUpdate**6. **updated**7. **beforeD…

8.15笔记

一、mycat读写分离实现 1. 添加一个新的虚拟主机&#xff0c;设置ip为10.1.1.60,主机名为mycat.yuanyu.zhangmin.关闭防火墙 SELinux NetworkManager 2. 上传jdk和mycat安装包 3. 解压并且添加到指定的位置 [rootmycat ~]# ls anaconda-ks.cfg frp initserver.sh jdk1.8…

018集——递归函数和for循环对比(从1加到100实例) ——C#学习笔记

本例分别用递归函数和for循环&#xff0c;求出1到100的和&#xff1a; using System;namespace Mytest {class Mytest{static void Main(string[] args){Calculate Myc new Calculate();int YourNumber 100;int Mysum Myc.Xto1(YourNumber);Console.WriteLine("从1加到…

Element-03.组件-Pagination分页

一.常见组件-分页-属性 参数&#xff1a;background 说明&#xff1a;是否为分页按钮添加背景色 类型&#xff1a;boolean 有background即添加&#xff0c;没有则不添加 参数&#xff1a;layout 说明&#xff1a;组件布局&#xff0c;子组件名用逗号分隔 类型&#x…

86.小米相机修改拍照(尺寸,画幅,比例)的方法

目录 1.打开相机&#xff0c;拍照模式&#xff0c;上面有个箭头或三个点&#xff0c;点击 2.点击画幅 3.点击你想要的画幅即可。 想要修改手机照片的&#xff08;尺寸&#xff0c;画幅&#xff0c;比例&#xff09;时&#xff0c;总会去找分辨率&#xff0c;其实并不是&…

用后端实现一个简单的登录模块2 前端页面

该模块能做到的功能&#xff1a; 1阶&#xff1a;输入账号和密码&#xff0c;输入正确即可返回登录成功的信息&#xff0c;反之则登录失败 2阶&#xff1a;有简单的前端页面&#xff0c;有登录成功和失败的弹窗&#xff0c;还有登录成功的主页面 3阶&#xff1a;前端页面的注…

探索Python的中文转换魔法:zhconv库的神秘力量

文章目录 探索Python的中文转换魔法&#xff1a;zhconv库的神秘力量第一部分&#xff1a;背景介绍第二部分&#xff1a;库的概述第三部分&#xff1a;安装指南第四部分&#xff1a;函数使用示例第五部分&#xff1a;实际应用场景第六部分&#xff1a;常见问题与解决方案第七部分…

【Vue3】路由Query传参

【Vue3】路由Query传参 背景简介开发环境开发步骤及源码总结 背景 随着年龄的增长&#xff0c;很多曾经烂熟于心的技术原理已被岁月摩擦得愈发模糊起来&#xff0c;技术出身的人总是很难放下一些执念&#xff0c;遂将这些知识整理成文&#xff0c;以纪念曾经努力学习奋斗的日子…

24/8/17算法笔记 策略梯度reinforce算法

import gym from matplotlib import pyplot as plt %matplotlib inline#创建环境 env gym.make(CartPole-v0) env.reset()#打印游戏 def show():plt.imshow(env.render(mode rgb_array))plt.show() show()定义网络模型 import torch #定义模型 model torch.nn.Sequential(t…