一 Ioc基础

1.什么是Ioc?

  Ioc(Inversion of Control)既控制反转,Ioc不是一种技术,而是一种思想,在Java开发中意味着将设计好的对象交给容器来进行控制,并不是像传统的程序一样在对象内部进行创建。

2.如何理解Ioc?

  在传统的程序中,当某个Java对象(调用者)需要调用另一个Java对象(被调用者,既被依赖对象)时,调用者通常会采用“new 调用者”的代码方式来创建对象。

  理解Ioc的关键在于要理解“谁控制谁,控制什么,为何是反转,哪些方面反转了”

  * 谁控制谁,控制什么:在传统的Java程序中,我们通常都是在一个类的内部直接创建一个对象(使用new),这样就是程序主动的去创建一个对象,控制权在程序,而在spring的Ioc中,是由一个专门的容器来创建这些对象,控制权不在程序了。谁控制谁?Ioc容器控制了对象。控制什么?Ioc容器主要控制了一个类对外部资源(对象,文件)的获取。

  *为何是反转,哪些方面反转了:

   有了反转,必定由正转:

   正转:在传统的程序中,是由自己在一个对象(一个类中)直接去创建一个1依赖对象,这就是正转。

   反转:反转就是由Ioc容器来创建对象并且给类注入此对象。

   为何是反转?因为是由容器来创建并且帮助注入依赖对象,对象并没有直接去创建(new)一个对象而是被动的接受依赖对象,所以是反转。

   哪些方面反转了?依赖对象的获取被反转了。

                  

                    传统应用程序示意图

                                  使用Ioc容器后的程序结构示意图

3.Ioc的优点

  Ioc不是一种技术,而是一种思想,是一个重要的面向对象的编程法则,他能指导我们如何设计出松耦合,更优良的程序,传统的应用程序是我们在类的内部主动创建依赖对象,从而导致类与类之间的高耦合,难以测试,有了Ioc容器后,由容器来创建和查找依赖对象,并给对象注入依赖对象,所以对象与对象之间是松散耦合,方便测试,利于功能复用。

  Ioc对编程带来的最大改变不是代码上,而是思想上,应用程序原本是老大,要获取什么资源都是主动的去创建,但是在Ioc思想种,应用程序就变动被动了,被动地等待Ioc容器来创建并注入它所需的资源。

  Ioc容器很好的体现了面向对象的设计法则之一:好莱坞法则“别找我们,我们找你”,即由Ioc容器来创建并注入对象,而不是由对象来找。

  

二 依赖注入

1.什么是依赖注入(DI)?

  依赖注入(DI)是控制反转(Ioc)的含义相同,只不过是从不同的角度来看待。

2.依赖注入的目的?

  依赖注入的目的并非是为系统带来更多的功能,而是为了提高组件的重用率,并为系统搭建一个灵活的可扩展的平台。

3.理解DI的关键?

  理解DI的关键是“谁依赖谁,为什么需要依赖,谁注入谁,注入了什么?”

  *谁依赖谁:应用程序依赖Ioc容器。

  *为什么需要依赖:应用程序需要Ioc容器来提供对象所需的资源。

  *谁注入谁:Ioc容器注入应用程序所需的依赖对象

  *注入了什么:注入了某个对象所需的外部资源。

4.Ioc和DI的关系

  Ioc和DI相当于一回事,只不过是看待问题的角度不同:

  Ioc:spring反向控制应用程序所需的资源;

  DI:应用程序依赖spring为其提供资源

5.依赖注入的方式

  依赖注入的作用是在使用spring框架时,动态地将其所依赖的对象注入到Bean组件中,其实现方法有两种:

  ☞ 属性setter方法注入:指的是spring容器使用setter方法注入被依赖的实例。通过调用无参构造器或者无参静态工厂方法实例化Bean后,调用该bean的setter方法,即可实现基于setter方法的依赖注入。

  ☞ 构造方法注入:指spring容器使用构造方法注入被依赖的实例。基于构造方法的依赖注入是通过调用带参数的构造方法来实现,每个参数代表着一个依赖。

  下面是使用setter方法来注入依赖对象

(1)创建一个UserDao接口,该接口中有一个方法say方法

package com.itheima.ioc;

public interface  UserDao {
public void say();
}

  (2)创建一个UserDaoImpl的类,该类实现了接口UserDao

package com.itheima.ioc;

public class UserDaoImpl implements UserDao {
@Override
public void say() {
System.out.println("UserDao say hello Word!"); }
}

  (3)创建一个UserService接口

package com.itheima.ioc;

public interface UserService {
public void say();
}

 (4)创建一个UserServiceImpl类,该类实现了UserService 接口,类中有一个属性UserDao,并且有一个方法setter,该方法是用于Ioc容器给UserServiceImpl注入UserDao对象。

package com.itheima.ioc;

public class UserServiceImpl implements UserService {

    //声明UserDao属性
private UserDao UserDao; //添加UserDao属性的setter方法
public void setUserDao(UserDao userDao) {
UserDao = userDao;
} //实现接口中的方法
@Override
public void say() {
//调用userDao的方法
this.UserDao.say();
System.out.println("userService say hello World!");
}
}

  

  (5)配置applicationContext.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-4.3.xsd"> <!-- 将指定的类配置给Spring,让Spring创建其对象的实例 -->
<bean id="userDao" class="com.itheima.ioc.UserDaoImpl"/> <!-- 添加一个id为userService的bean -->
<bean id="userService" class="com.itheima.ioc.UserServiceImpl">
<!-- 将id为userDao的bean实例注入到user Service实例中 -->
<property name="userDao" ref="userDao"/>
</bean>
</beans>

  <property>元素是<bean>元素的子元素,它用于调用Bean实例中的setUserDao()方法完成属性赋值,从而实现依赖注入。其name属性表示Bean实例中相应属性名,ref属性用于指定属性值。

  (6)Test测试类

package com.itheima.ioc;

import org.springframework.context.ApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;

public class DITest {
public static void main(String[] args) {
//1.初始化spring容器,加载配置文件
ApplicationContext applicationContext=
new ClassPathXmlApplicationContext("applicationContext.xml");
//2.通过容器来获取UserService实例
UserService userService=(UserService) applicationContext.getBean("userService");

//3.调用实例中的方法
userService.say();
}
}

  (7)程序结果

  

三 Ioc容器

  容器中的两种表示形式:BeanFactory 和ApplicationContext

  springIoc把BeanFactory的实现当作低级容器,把ApplicationContext的实现当作高级容器

1.两个容器之间的区别:

  BeanFactory:容器在启动的时候并不会实例化bean,只有当用户调用getBean时才会对配置好的bean进行实例化。

  ApplicationContext容器:当容器启动时,容器就已经实例化好了所有配置的bean。

2.如何延迟实例化:

  对于在ApplicationContext容器启动便进行了实例化,可以通过两种方法来延迟实例化:

  ☞ 可以在bean元素配置lazy-init=true来让bean延迟实例化;

  ☞ 可以在beans元素里配置lazy-init=true来让这个beans里的所有bean都延迟实例化;

3.如何选择延迟化和非延迟化

  ☞ 对于系统资源比较少的可以使用延迟实例化;

  ☞ 对于web应用,一般选择迫切实例化;

  ☞ 在web应用中,我们一般把比较耗时的事情放在系统启动的时候完成;

spring学习之依赖注入DI与控制反转IOC的更多相关文章

  1. PHP依赖注入(DI)和控制反转(IoC)详解

    这篇文章主要介绍了PHP依赖注入(DI)和控制反转(IoC)的相关资料,具有一定的参考价值,感兴趣的小伙伴们可以参考一下 首先依赖注入和控制反转说的是同一个东西,是一种设计模式,这种设计模式用来减少程 ...

  2. 依赖注入(DI)和控制反转(IOC)

    依赖注入(DI)和控制反转(IOC) 0X1 什么是依赖注入 依赖注入(Dependency Injection),是这样一个过程:某客户类只依赖于服务类的一个接口,而不依赖于具体服务类,所以客户类只 ...

  3. 依赖注入(DI)和控制反转(IOC)的理解,写的太好了。

    学习过spring框架的人一定都会听过Spring的IoC(控制反转) .DI(依赖注入)这两个概念,对于初学Spring的人来说,总觉得IoC .DI这两个概念是模糊不清的,是很难理解的,今天和大家 ...

  4. 【串线篇】依赖注入DI与控制反转IOC

    DI&IOC 在spring框架中DI与IOC说的其实是一回事 一句话:本来我接受各种参数来构造一个对象,现在只接受一个参数——已经实例化的对象. 也就是说我对对象的『依赖』是注入进来的,而和 ...

  5. 轻松理解 Java开发中的依赖注入(DI)和控制反转(IOC)

    前言 关于这个话题, 网上有很多文章,这里, 我希望通过最简单的话语与大家分享. 依赖注入和控制反转两个概念让很多初学这迷惑, 觉得玄之又玄,高深莫测. 这里想先说明两点: 依赖注入和控制反转不是高级 ...

  6. 话说 依赖注入(DI) or 控制反转(IoC)

    科普:首先依赖注入和控制反转说的是同一个东西,是一种设计模式,这种设计模式用来减少程序间的耦合,鄙人学习了一下,看TP官网还没有相关的文章,就写下这篇拙作介绍一下这种设计模式,希望能为TP社区贡献一些 ...

  7. ASP.NET MVC进阶之路:深入理解依赖注入(DI)和控制反转(IOC)

    0X1 什么是依赖注入 依赖注入(Dependency Injection),是这样一个过程:某客户类只依赖于服务类的一个接口,而不依赖于具体服务类,所以客户类只定义一个注入点.在程序运行过程中,客户 ...

  8. PHP 依赖注入(DI) 和 控制反转(IoC)

    要想理解 PHP 依赖注入 和 控制反转 两个概念,就必须搞清楚如下的两个问题: DI —— Dependency Injection 依赖注入 IoC —— Inversion of Control ...

  9. 聊一聊PHP的依赖注入(DI) 和 控制反转(IoC)

    简介 IoC Inversion of Control 控制反转DI Dependency Injection 依赖注入 依赖注入和控制反转说的实际上是同一种东西,它们是一种设计模式,这种设计模式用来 ...

随机推荐

  1. 【机器学习实战学习笔记(2-2)】决策树python3.6实现及简单应用

    文章目录 1.ID3及C4.5算法基础 1.1 计算香农熵 1.2 按照给定特征划分数据集 1.3 选择最优特征 1.4 多数表决实现 2.基于ID3.C4.5生成算法创建决策树 3.使用决策树进行分 ...

  2. [HNOI2008] 玩具装箱 D2 T3 斜率优化DP

    Description P教授要去看奥运,但是他舍不下他的玩具,于是他决定把所有的玩具运到北京.他使用自己的压缩器进行压缩,其可以将任意物品变成一堆,再放到一种特殊的一维容器中.P教授有编号为1... ...

  3. Elasticsearch 批处理

    章节 Elasticsearch 基本概念 Elasticsearch 安装 Elasticsearch 使用集群 Elasticsearch 健康检查 Elasticsearch 列出索引 Elas ...

  4. office(CVE-2012-0158)漏洞分析报告

    2019/9/12 1.漏洞复现 ①发现崩溃 ②找到漏洞所在的函数,下断点,重新跑起来,单步调试,找到栈被改写的地方 ③分析该函数 把MSCOMCTL拖入IDA,查看该函数代码 ④查看调用栈,回溯. ...

  5. ROS2学习日志:QoS学习日志

    QoS学习日志 参考:ROS2API 及 https://index.ros.org/doc/ros2/Concepts/About-Quality-of-Service-Settings 1.概述 ...

  6. Java 第一次课堂测试总结。

    Java 第一次课堂测试总结. 昨天参加了JAVA的开学测试,课上没有完成计算基点的功能,以下是修改完成后的代码.  首先是ScoreInformation类来存储学生信息. //信1805-1 王正 ...

  7. python常用代码、问题汇总

    1.生成dataframe数据 5.读取带 ','分隔符的txt文件 4.DataFrame格式数据处理中报错 2.安装库时出现如下错误: 3.得到股票交易日数据 1.生成dataframe数据 im ...

  8. 4K电视到底值不值得购买?

    在智能手机等移动终端的冲击下,近年来电视厂商的日子越来越不好过.为了吸引消费者的关注,电视厂商也是绞尽脑汁不断在电视上增加各种噱头功能.比如当年被吹得神乎其神.在家就享受影院体验的3D电视,就因为3D ...

  9. SpringBoot基于easyexcel导出和写入Excel

      easyexcel是阿里巴巴旗下开源项目,主要用于Excel文件的导入和导出处理,今天我们利用SpringBoot和easyexcel实战演示如何导出和写入Excel文件. 一.加入我们需要的ea ...

  10. C++基础--转string

    在C++中,任意数值型转可以使用字符串流的方式来实现,如果编译器支持C++11标准的话,也可以用to_string()函数来实现. 1.to_string() to_string()包含在头文件< ...