Spring框架----->(1) 深入解剖Spring概念和IoC控制反转核心技术

一、何为Spring框架

1、Spring概述:

它是为了减轻对项目模块之间的管理,类和类之间的管理, 帮助开发人员创建对象,管理对象之间的关系。

2、Spring核心技术:
(1)控制反转(IoC)

IoC:能实现模块之间,类之间的解耦合,即不用再自己创建要使用的对象了。而是由 Spring容器统一管理,自动“注入”,注入即赋值。

(2)面向切面编程(AOP)

AOP:使得系统级服务得到了最大复用,且不用再由程序员手工将系统级服务“混杂”到主业务逻辑中了,而是由 Spring 容器统一完成“织入”。

3、优点:
  • 1、轻量级
  • 2、针对接口编程,解耦合
  • 3、AOP编程的支持

二、IoC控制反转

1、IoC (Inversion of Control) : 控制反转, 是一个理论,概念,思想。

(1)控制反转:把对象的创建,属性赋值,依赖的管理工作都交给代码之外的容器实 现, 也就是对象的创建是有其它外部资源完成。

(2)控制:创建对象,对象的属性赋值,对象之间的关系管理。

(3)反转: 把原来的开发人员管理,创建对象的权限转移给代码之外的容器实现。 由 容器代替开发人员管理对象。创建对象,给属性赋值。

(4)正转:由开发人员在代码中,使用new 构造方法创建对象, 开发人员主动管理 对象。

public static void main(String args[ ]){
    
    
     Student student = new Student( ); // 在代码中, 创建对象。
}

(5)容器:是一个服务器软件, 一个框架(spring)

2、java中创建对象有哪些方式:
  • 1. 构造方法,new 对象
  • 2. 反射
  • 3. 序列化
  • 4. 克隆
  • 5. ioc :容器创建对象
  • 6. 动态代理

这里我们以前也学过ioc的思想了,例如servlet :
1、创建类继承HttpServelt
2、在web.xml 注册servlet , 使用
< servlet-name> myservlet < /servlet-name>
< servelt-class>com.hcz.controller.MyServlet< /servlet-class >
3、这里并没有没有创建 过Servlet对象, 也就是没有 MyServlet myservlet = new MyServlet()
4、这个Servlet对象是由Tomcat服务器它能你创建的。 Tomcat也称为容器
5、Tomcat作为容器:里面存放的有Servlet对象, 监听器Listener , 过滤器Filter对象

3、为什么要使用IoC呢?

目的就是减少对代码的改动, 也能实现不同的功能。 实现解耦合。

4、IoC的实现方式
  • DI(Dependency Injection)依赖注入:

若需要调用另一个对象协助时,无须在代码中创建被调用者,只需要在程序中提供要使用的对象名称就可以, 至于对象如何在容器中创建,赋值,查找都由容器内部实现,再由容器传给程序。

  • Spring框架使用依赖注入实现IoC:

1、Spring是一个容器,管理对象,给属性赋值,底层是反射创建对象
2、Spring 容器是一个超级大工厂,负责创建、管理所有的 Java 对象,这些 Java 对象被称为 Bean
3、Spring 容器管理着容器中 Bean 之间的依赖关系,Spring 使用“依赖注入”的方式来管理 Bean 之间的依赖关系

三、创建第一个Spring程序

(1)先创建maven项目

在这里插入图片描述

(2)引入maven依赖pom.xml
<dependency>
  <groupId>org.springframework</groupId>
  <artifactId>spring-context</artifactId>
  <version>5.2.3.RELEASE</version>
</dependency>
(3)定义接口与实体类
public interface SomeService {
    
    
    public void doSome();
}
public class SomeServiceImpl implements SomeService {
    
    
    public SomeServiceImpl(){
    
    
        System.out.println("无参构造方法");
    }
    @Override
    public void doSome() {
    
    
        System.out.println("执行了SomeService的doSome方法");
    }
}
(4)创建Spring配置文件
在 src/main/resources/目录现创建一个 xml 文件,文件名可以随意,但 Spring 建议的名称为 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.xsd">

    <bean id="someService" class="com.hcz.service.impl.SomeServiceImpl"/>
    <bean id="someService1" class="com.hcz.service.impl.SomeServiceImpl"/>

    <!--创建一个非定义类的对象-->
    <bean id="myDate" class="java.util.Date"/>
</beans>

解析
1、< bean >:用于创建实例对象,一个实例对象对应一个bean标签
2、id属性:对象的自定义名称,它是唯一值,spring通过这个id值来找到这个实例对象
3、class属性:类的全限定名称(注意:不能是接口,因为Spring是反射机制创建对象,必须使用类)

Spring底层实现原理
SomeService someService = new SomeServiceImpl();
spring是把创建好的对象放入到map中,spring框架有一个map存放对象的 ,springMap.put(id值,对象);
例如:
springMap.put("someService",new SomeSerivceImp());

(5)定义测试类
/**
 * 1、不使用spring容器创建对象
 */
@Test
public void testSomeServiceOne(){
    
    
    SomeService service = new SomeServiceImpl();
    service.doSome();
}

/**
 * 2、使用spring容器创建对象
 */
@Test
public void testSomeServiceTwo(){
    
    
    
    //1.指定spring的配置文件
    String config = "bean.xml";
    //2.创建spring容器的【所有对象】,因为调用了它们各自的无参构造方法
    ApplicationContext context = new ClassPathXmlApplicationContext(config);
    //3.从容器中获取某个对象
    SomeService someService = (SomeService) context.getBean("someService");
    someService.doSome();
}

解析
1、ApplicationContext:表示IOC容器的入口,会在容器对象初始化时,将其中的所有对象一次性全部装配好。以后代码中若要使用到这些对象,只需从内存中直接获取即可。执行效率较高。但占用内存。
该类有两个读取配置文件的实现类:

  • ClassPathXmlApplicationContext:表示从类路径classpath中读取数据>
  • FileSystemXmlApplicationContext:表示从当前文件系统中读取数据

2、器中的实例对象是什么时候创建的 ?
容器中的对象在创建spring容器时就已经把对象创建好了

3、使用Spring容器创建对象的原理图
在这里插入图片描述

4、spring容器中不仅定义获取某个对象的方法,还定义了获取spring容器中实例对象的数量和各自的对象名称

//3.从容器中获取容器中定义的对象的数量
int num = context.getBeanDefinitionCount();

//4.获取容器中每个定义的对象的名称
String[] names = context.getBeanDefinitionNames();

5、spring容器还可以获取非自定义类,例如:Date日期类

在配置文件中定义

<bean id="myDate" class="java.util.Date"/>

定义测试方法

@Test
public void testSomeServiceFour(){
    
    
    //1.指定spring的配置文件
    String config = "bean.xml";
    //2.创建spring容器中的所有对象
    ApplicationContext context = new ClassPathXmlApplicationContext(config);
    //3.从容器中获取某个对象
    Date myDate = (Date) context.getBean("myDate");
    System.out.println(myDate);
}

如有不足之处请大家指正哈!

猜你喜欢

转载自blog.csdn.net/hcz666/article/details/113190638