三大框架之一Spring

 

目录

一、简介

二、spring框架

1、框架组成

2、核心概念

 3、三大核心组件的关系

4、Spring框架两大核心:IoC和DI

4.1、IOC解释

 4.2、DI解释

三、实现IOC的两种方式

1、XML的方式实现IOC的步骤

        1.1、创建类

        1.2、创建配置文件,配置类的信息

        1.3、读取配置文件,直接获取对象

1.4、总结

2、注解方式实现IOC

2.1、创建类,使用注解

2.2、创建配置文件,扫描包,只需要指定包的路径

2.3读取配置文件,获取对象,调用方法

2.4、总结

3、注解方式实现不同包下多个类的 IOC

1)创建多个不同的包名,分别创建各自的类

2)配置文件

3)测试读取配置文件,获取对象,调用方法

四、模拟IOC

1、创建Bean类,描述类的信息

2、创建Spring容器,并指定要维护的类,提供getBean(),根据beanName获取对象

3、创建指定的Hello、User类

4、创建测试类

5,总结

五、DI依赖注入

1、概述

2、不使用DI使两个类建立关系的方法

2.1、创建Maven工程module

 3、使用SpringDI依赖注入时的步骤

3.1、创建Teacher类

3.2、创建Student类

3.3 创建核心配置文件,配置包扫描的路径

3.4测试,读取配置文件,向下造型回去子类的属性和功能

 3.5、总结

六、面试题

面试:IoC和DI

自动装配

七、Spring自动装配过程

1、 Spring"容器"

 2、依赖注入的原理

八、MVC项目

1、布置项目结构

 2、修改端口号

3、创建前端html网页添加数据

4、创建启动类RunApp

5、pojo包下创建Car类

6、controller包下创建CarController类

7、service包下创建CarService接口

8、service包下创建CarServiceImpl实现类

9、测试


一、简介

经典的三层框架诞生SSH (Strut2+Spring+Hibernate),新三大框架诞生,SSM(SpringMVC+Spring+MyBatis),SpringBoot+SpringCloud 微服务

二、spring框架

安装地址:http://spring.io

1、框架组成

Spring是一个开源框架,是为了解决企业应用程序开发复杂性而创建的。

Spring 框架是一个分层架构,由7个定义良好的模块组成。Spring 模块构建在核心容器之上,核心容器定义了创建、配置和管理 bean 的方式,如下图所示:

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-jsPyvCdC-1623125484732)(RackMultipart20210608-4-9jbi5w_html_f6b76c48c15a8c6e.jpg)]

组成 Spring 框架的每个模块(或组件)都可以单独存在,或者与其他一个或多个模块联合实现 

每个模块的功能如下:

Spring 框架的功能可以用在任何J2EE服务器中,大多数功能也适用于不受管理的环境。Spring 的核心要点是:支持不绑定到特定J2EE服务的可重用业务和数据访问对象。毫无疑问,这样的对象可以在不同J2EE环境(Web或EJB)、独立应用程序、测试环境之间重用。

Spring以一种非侵入式的方式来管理你的代码,Spring提倡"最少侵入",这也就意味着你可以适当的时候安装或卸载Spring ,但这点越来越模糊。

2、核心概念

 

 3、三大核心组件的关系

Bean、Context、Core三大核心组件的关系:

Bean 包装的是 Object,而 Object 必然有数据,如何给这些数据提供生存环境就是 Context要解决的问题。bean的作用域:singleton表示一个bean定义对应一个实例。 prototype表示一个bean定义对应多个实例。 singleton是缺省值。在设计bean时,依据实际业务的需要,可以为bean提供相应的生命周期方法,比如在初始化方法当中完成资源加载等类似的逻辑,在销毁方法中释放资源。因此bean当中是否有生命周期相关的方法,完成取决于实际业务需要,并不是必须的.

对 Context 来说它就是要发现每个 Bean 之间的关系,为它们建立这种关系并且要维护好这种关系。所以 Context 就是一个Bean关系的集合,这个关系集合又叫 Ioc 容器,一旦建立起这个 Ioc 容器后 Spring 就可以为你工作了。

Core 就是发现、建立和维护每个 Bean 之间的关系所需要的一些类的工具,从这个角度看来,Core 这个组件叫 Util 更能让你理解。

把Bean 比作一场演出中的演员的话,那 Context 就是这场演出的舞台背景,而 Core应该就是演出的道具了。只有他们在一起才能具备能演出一场好戏的最基本的条件。当然有最基本的条件还不能使这场演出脱颖而出,还要他表演的节目足够的精彩,这些节目就是 Spring 能提供的特色功能。

4、Spring框架两大核心:IoC和DI

1)IoC(Inversion of Control)简单来说就是将对象Object的创建的权力及对象的生命周期的管理过程交由Spring框架来处理,从此在开发过程中不在需要关注对象的创建和生命周期的管理,而是在需要的时候由Spring框架提供,这个由Spring框架管理对象创建和生命周期的机制称之为控制反转。对象只是被动的接收依赖对象。
2)在创建对象的过程中Spring可以依据对象的关系,自动把其它对象注入(无需创建对象,直接拿着使用)进来,这个过程称之为DI(Dependency Injection)依赖注入。

3)总结下Spring核心就干了两件事:

  1. 创建对象
  2. 设置对象的关联关系

4.1、IOC解释

IOC(Inversion of Control),控制反转。是把管理对象的权利交给spring框架。

ioc的过程就是创建对象的过程(new对象)

就是指将对象的创建,对象的存储(map),对象的管理(依赖查找,依赖注入)都交给了spring容器。

两种方式:xml方式实现ioc、注解方式实现ioc

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-FXpxKfc1-1623125484736)(RackMultipart20210608-4-9jbi5w_html_cffa20c878203547.png)]

 4.2、DI解释

相对于IoC而言,依赖注入(DI)更加准确地描述了IoC的设计理念。所谓依赖注入,即组件之间的依赖关系由容器在应用系统运行期来决定,也就是由容器动态地将某种依赖关系的目标对象实例注入到应用系统中的各个关联的组件之中。

IOC具有三种注入方式,分别是构造函数注入、属性注入和接口注入。

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-hhlhCGxn-1623125484738)(RackMultipart20210608-4-9jbi5w_html_c5ec83eb26f6a77c.png)]

三、实现IOC的两种方式

1、XML的方式实现IOC的步骤

该方式了解即可

1.1、创建类

package cn.tedu.spring;

public class Hello {
    void hi(){
        System.out.println("hello spring ioc~ ");
    }
}

1.2、创建配置文件,配置类的信息

选中resources-右键-new-xml config…-spring config-输入文件名-回车

<?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">

     <!-- 配置一个类的信息 id是bean的唯一标识  class是类的全路径,找到类名copy reference粘贴过来即可-->
    
<bean id="hello" class="cn.tedu.spring.Hello"></bean>
    
</beans>

1.3、读取配置文件,直接获取对象

package cn.tedu.test;
import org.junit.jupiter.api.Test;
import org.springframework.context.support.ClassPathXmlApplicationContext;

public class TestIOC {
    //单元测试junit方法:@Test public void 没有参数
    @Test
    public void ioc(){
        //1.读取配置文件--参数是文件的路径
        ClassPathXmlApplicationContext spring =
                                             /*配置文件名也要一致,否则报错*/
                new ClassPathXmlApplicationContext("spring-config.xml");
        //2.获取对象--参数是配置文件里bean的id属性值
        //属性值大小写一定要一致,否则找不到,报错
        Object o = spring.getBean("hello");
        //打印地址值
        System.out.println(o);//cn.tedu.spring.Hello@302552ec
		
        //o.hi();父类不能使用子类的特有功能
        //解决办法:向下造型,专门使用子类的资源
        Hello h = (Hello) o ;
        //默认的权限修饰符的方法不能被调用,要改为public才行
        h.hi();
    }

}

1.4、总结

在这里插入图片描述

2、注解方式实现IOC

哪个类想让spring框架new对象,就在类上使用注解:@Component / @Service / @Controller   使用其中一个就可以

2.1、创建类,使用注解

package cn.tedu.spring2;

import org.springframework.stereotype.Component;

//Map<类名首字母要小写,类的对象> - {user=new User()}
@Component
public class User {
    public void get(){
        System.out.println("hello springioc");
    }
}

2.2、创建配置文件,扫描包,只需要指定包的路径

在这里插入图片描述

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
       xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
       xmlns:context="http://www.springframework.org/schema/context"
       xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd http://www.springframework.org/schema/context https://www.springframework.org/schema/context/spring-context.xsd">

    <!-- 包扫描:只需要指定从哪个包开始扫描,
        用了@Component注解的类,自动ioc
        base-package需要指定一个包的路径
    -->
    <context:component-scan base-package="cn.tedu.spring2"></context:component-scan>

</beans>

2.3读取配置文件,获取对象,调用方法

配置文件可以有多个,也可以在一个配置文件操作

package cn.tedu.test;

import org.junit.jupiter.api.Test;
import org.springframework.context.support.ClassPathXmlApplicationContext;
//测试 注解开发
public class TestIOC2 {
    @Test
    public void ioc2(){
        //1,读取核心配置文件
        ClassPathXmlApplicationContext spring =
                new ClassPathXmlApplicationContext(
                        "spring-config2.xml");
        //2,getBean -- 参数是类名,但是首字母要变成小写才行
        Object o = spring.getBean("user");
        System.out.println(o);//cn.tedu.spring2.User@37d4349f

        Object o2 = spring.getBean("userInfo");
        System.out.println(o2);//cn.tedu.spring2.UserInfo@2805d709

    }
}

2.4、总结

在这里插入图片描述

3、注解方式实现不同包下多个类的 IOC

1)创建多个不同的包名,分别创建各自的类

包名:cn.tedu.spring---Hello类--创建hi()方法

包名:cn.tedu.annocation---User类和UserInfo类--创建get()方法和eat()方法

注意:所有的类上都要加注解@Component

2)配置文件

resources-->spring-Config2.xml

3)测试读取配置文件,获取对象,调用方法

package cn.tedu.test;

import cn.tedu.annotation.User;
import cn.tedu.annotation.UserInfo;
import cn.tedu.spring.Hello;
import org.junit.jupiter.api.Test;
import org.springframework.context.support.ClassPathXmlApplicationContext;

public class TestAll {
    @Test
    public void ioc(){
        //1.读取配置文件
        ClassPathXmlApplicationContext spring =
                new ClassPathXmlApplicationContext(
                        "spring-Config2.xml");
        //2.通过map<k,v>中的k值,即类名获取对应的对象(全路径名)
        Object o1 = spring.getBean("hello");
        System.out.println(o1);//打印地址值
        //3.向下造型获取指定对象的方法
        Hello hello = (Hello)o1;
        hello.hi();//调用方法

        Object o2 = spring.getBean("user");
        System.out.println(o2);
        User user = (User) o2;
        user.get();

        Object o3 = spring.getBean("userInfo");
        System.out.println(o3);
        UserInfo userInfo = (UserInfo) o3;
        userInfo.eat();
    }
}

四、模拟IOC

1、创建Bean类,描述类的信息

package cn.tedu.myioc;
//描述一个类的信息,spring把每个类当做一个bean
public class Bean {
    private String beanName;//类的名字
    private String beanPath;//类的全路径
    //提供构造方法constructors
    public Bean(){}
    public Bean(String beanName, String beanPath) {
        this.beanName = beanName;
        this.beanPath = beanPath;
    }
    //get set tostring
    public String getBeanName() {
        return beanName;
    }
    public void setBeanName(String beanName) {
        this.beanName = beanName;
    }
    public String getBeanPath() {
        return beanPath;
    }
    public void setBeanPath(String beanPath) {
        this.beanPath = beanPath;
    }
    @Override
    public String toString() {
        return "Bean{" +
                "beanName='" + beanName + '\'' +
                ", beanPath='" + beanPath + '\'' +
                '}';
    }
}


/**或者使用Lombok*/
package cn.tedu.design;

import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;
import lombok.experimental.Accessors;
/*Lombok插件省略set、get、tostring()*/
@Data
@NoArgsConstructor
@AllArgsConstructor
@Accessors(chain = true)
public class Bean {
    private String name;
    private String path;
}

2、创建Spring容器,并指定要维护的类,提供getBean(),根据beanName获取对象

package cn.tedu.myioc;

import org.springframework.context.support.ClassPathXmlApplicationContext;

import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

public class MyIOC {
    //1,创建list,存好多bean,有序有下表
    private List<Bean> beans = new ArrayList<>();
    public MyIOC() throws Exception {
        Bean b1 = new Bean("hello","cn.tedu.myioc.Hello");
        Bean b2 = new Bean("user","cn.tedu.myioc.User");
        beans.add(b1);//把指定对象添加到beans集合
        beans.add(b2);
        
        init();//自定义方法--用于反射遍历,创建全路径对象
    }
    //准备spring容器Map<k,v>,特点:无序无下标不可重复,唯一性
    //Map<String,Object> map = new HashMap<>();
     Map<String,Object> map = new ConcurrentHashMap<>
    //2,创建map,存对象 { hello=new Hello() , user=new User()}
    public void init() throws Exception {
        //遍历list,获取每个bean
        for(Bean b : beans){
            String key = b.getBeanName();
            String quanlujing = b.getBeanPath();
            Object value = Class.forName(quanlujing).newInstance();
            map.put(key,value);
           //map键值对不够安全,多线程抢占时并发所以把HashMap<>转为ConcurrentHashMap<>
        }
    }
    //3,getBean()--根据key获取value
    public Object getBean(String beanname){
        return map.get(beanname) ;
    }
}

3、创建指定的Hello、User类

在这里插入图片描述

4、创建测试类

package cn.tedu.test;

import cn.tedu.design.User;
import cn.tedu.design.Hello;
import cn.tedu.design.SpringContext;

public class TestMyIOC {
    public static void main(String[] args) throws Exception {
        SpringContext spring = new SpringContext();
        Hello h = (Hello)spring.getBean("hello");
        System.out.println(h);//获取地址值
        o.get();//如果类里有方法可以进行调用

        User user = (User) spring.getBean("user");
        System.out.println(user);
        user.find();
    }
}

5,总结

在这里插入图片描述

五、DI依赖注入

1、概述

依赖注入,前提是先使用注解@Component完成IOC

使用DI注解@Autowired ,使两个类(对象)之间建立关系

2、不使用DI使两个类建立关系的方法

2.1、创建Maven工程module

创建Dept类

package cn.tedu.pojo;

import org.springframework.stereotype.Component;

@Component//交给spring进行ioc
public class Dept {
    public String name = "java研发部门";
    @Override
    public String toString() {
        return "Dept{" +
                "name='" + name + '\'' +
                '}';
    }
}

创建User类

package cn.tedu.pojo;

import org.springframework.stereotype.Component;

@Component//交给spring进行ioc
public class User {
    String name = "蔡徐坤";
    //描述User类和Dept类的关系
    private Dept d;
    public void setD(Dept d) {
        this.d = d;
    }
    public Dept getD() {
        return d;
    }
    @Override
    public String toString() {
        return "User{" +
                "name='" + name + '\'' +
                ", d=" + d +
                '}';
    }
}

测试

在这里插入图片描述

package cn.tedu.di;

import cn.tedu.pojo.Dept;
import cn.tedu.pojo.User;

public class Test1 {
    public static void main(String[] args) {
        User u = new User();
    //先设置部门信息,否则永远获取的是null
        u.setD(new Dept());
        //获取用户的部门信息
        Dept dept = u.getD();
        //获取部门名称
        System.out.println(dept.name);
    }
}

 3、使用SpringDI依赖注入时的步骤

3.1、创建Teacher类

package cn.tedu.vo;

import org.springframework.stereotype.Component;

@Component//ioc
public class Teacher {
    public String name = "jack" ;
    @Override
    public String toString() {
        return "Teacher{" +
                "name='" + name + '\'' +
                '}';
    }
}

3.2、创建Student类

两个类建立关系,DI提供注解@Autowired

package cn.tedu.vo;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;

@Component//ioc
public class Student {
    public String name = "蔡徐坤" ;
    // 表示两个类之间的关系
    @Autowired//DI依赖注入,自动装配,自动布线
    Teacher t ;
    @Override
    public String toString() {
        return "Student{" +
                "name='" + name + '\'' +
                ", t=" + t +
                '}';
    }
}

3.3 创建核心配置文件,配置包扫描的路径

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
       xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
       xmlns:context="http://www.springframework.org/schema/context"
       xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd http://www.springframework.org/schema/context https://www.springframework.org/schema/context/spring-context.xsd">

    <!--包扫描:扫描指定包路径下的所有类
        哪些类有@Component注解,就帮哪些类new-ioc
    -->
    <context:component-scan base-package="cn.tedu.vo"></context:component-scan>
</beans>

3.4测试,读取配置文件,向下造型回去子类的属性和功能

在这里插入图片描述

package cn.tedu.di;

import cn.tedu.vo.Student;
import cn.tedu.vo.Teacher;
import org.springframework.context.support.ClassPathXmlApplicationContext;

//测试springdi
public class Test2 {
    public static void main(String[] args) {
        //1,读取核心配置文件
        ClassPathXmlApplicationContext spring =
                new ClassPathXmlApplicationContext(
                        "spring-config.xml");
        //2,根据类名,获取对象
        //右侧返回的是Object父类,左侧要子类--需要强转--向下转型--是为了使用子类的功能
        Teacher t = (Teacher) spring.getBean("teacher");
        System.out.println(t);//Teacher{name='jack'}

        Student s = (Student) spring.getBean("student");
        //DI:在获取学生信息的同时,也获取到了关联的老师信息
        System.out.println(s);//Student{name='蔡徐坤', t=Teacher{name='jack'}}
    }
}

 3.5、总结

在这里插入图片描述

六、面试题


面试:IoC和DI


在平时的java应用开发中,我们要实现某一个功能或者说是完成某个业务逻辑时可能需要多个对象来协作完成,在没有使用Spring的时候,每个对象在需要使用他的合作对象时,自己均要使用像new object() 这样的语法来将合作对象创建出来,这个合作对象是由自己主动创建出来的,创建合作对象的主动权在自己手上,自己需要哪个合作对象,就主动去创建,创建合作对象的主动权和创建时机是由自己把控的,而这样就会使得对象间的耦合度高了,A对象需要使用合作对象B来共同完成一件事,A要使用B,那么A就对B产生了依赖,也就是A和B之间存在一种耦合关系,并且是紧密耦合在一起,而使用了Spring之后就不一样了,创建合作对象B的工作是由Spring来做的,Spring创建好B对象,然后存储到一个容器里面,当A对象需要使用B对象时,Spring就从存放对象的那个容器里面取出A要使用的那个B对象,然后交给A对象使用,至于Spring是如何创建那个对象,以及什么时候创建好对象的,A对象不需要关心这些细节问题(你是什么时候生的,怎么生出来的我可不关心,能帮我干活就行),A得到Spring给我们的对象之后,两个人一起协作完成要完成的工作即可。

所以控制反转IoC(Inversion of Control)是说创建对象的控制权进行转移,以前创建对象的主动权和创建时机是由自己把控的,而现在这种权力转移到第三方,比如转移交给了IoC容器,它就是一个专门用来创建对象的工厂,你要什么对象,它就给你什么对象,有了 IoC容器,依赖关系就变了,原先的依赖关系就没了,它们都依赖IoC容器了,通过IoC容器来建立它们之间的关系。

DI(依赖注入)其实就是IOC的另外一种说法,DI是由Martin Fowler 在2004年初的一篇论文中首次提出的。他总结:控制的什么被反转了?就是:获得依赖对象的方式反转了。

IoC是设计思想,IoC有三个核心:BeanFactory、反射、DI。BeanFactory利用反射实现对象的创建,DI实现对象关系管理。

自动装配


利用注解方式,我们只需要写@Autowired注解,底层就会去容器中找对应的对象,如果有获取到,反射调用其对应的set方法,设置。而这个调用过程都是自动,我们没有手工去写set方法。所以这个过程也称为自动装配。
 

七、Spring自动装配过程

1、 Spring"容器"

说明: Spring容器是在内存中一大块的内存区域,存储Spring管理对象
数据结构: KEY-VALUE结构
数据类型: Map集合
Map详细说明: Key: 类型首字母小写 Value: 对象

 2、依赖注入的原理

1.按照类型注入
按照属性的类型 去Map集中中查找是否有改类型的对象. 如果有则注入.

2.按照名称注入 根据属性的name 去Map集中中查找对应的KEY

举例:Controller层根据名称注入自动装配

	@Autowired
    @Qualifier(value="李四")
    private SpringService springService;

自动装配的规则说明:
1.如果对象在进行实例化.如果对象中的属性被 @Autowired注解修饰,则说明应该先注入属性.
2.先根据属性的类型,查找Map集合中是否有该类型的对象.
3.如果根据类型查找没有找到,则根据属性的名称按照name查找对象.
4.如果上述的方式都没有找到,则报错实例化对象失败.

原则:Spring容器中要求 接口必须单实现. 如果有多实现则通过@Qualifier(“xxxx”),指定具体哪个实现来区分即可
 

八、MVC项目

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-cPl5tW93-1623125484759)(RackMultipart20210608-4-9jbi5w_html_a71a298b5faabd1f.png)]

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-lwPTMiRw-1623125484761)(RackMultipart20210608-4-9jbi5w_html_dce2bb2f55ba2790.png)]

需求:

前端:访问链接: http://localhost:8080/car/get

后端:得到JSON数据: {"name":"保时捷","color":"红色","price":641000.0}

1、布置项目结构

cn.tedu — 放启动类,存子包,启动类必须放在大范围包下,才能启动大包下的小包们
cn.tedu.service — 子包,放spring层的代码,接口 + 实现类
cn.tedu.controller — 子包,放springmvc的代码,controller负责接受请求做出响应
cn.tedu.pojo — 子包,放Model层的代码,用来封装数据

在这里插入图片描述

 2、修改端口号

src-->resources-->右键new-->file填写内容格式:

3、创建前端html网页添加数据

<!DOCTYPE html>
<html>
	<head>
		<meta charset="utf-8">
		<title>测试 框架整合</title>
	</head>
	<body>
		<a href="http://localhost:8090/car/get">点我请求汽车的数据</a>
	</body>
</html>

4、创建启动类RunApp

package cn.tedu;

import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
//启动类:启动服务器且默认开启包扫描,自动ioc,基于启动类所在的包,所以不需要包扫描的配置文件(.xml文件)
@SpringBootApplication
public class RunApp {
    public static void main(String[] args) {
        SpringApplication.run(RunApp.class);
    }
}

5、pojo包下创建Car类

Lombok插件先下载,才能使用注解,使用注解时再导包

package cn.tedu.pojo;

import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;
import lombok.experimental.Accessors;
import org.springframework.stereotype.Component;

/*使用Lombok注解时注意添加依赖包
* 替代set、get、toString()、equals、hashCode*/
@Data
@NoArgsConstructor
@AllArgsConstructor
@Accessors(chain = true)

@Component/*spring提供的ioc*/
public class Car {
    private Integer id;
    private String name;
    private String type;
    private String color;
    private Double price;
}

6、controller包下创建CarController类

目前依赖注入的是实现类。以后可以依赖注入接口,接口有多个实现类,想使用哪个实现类都可以

package cn.tedu.controller;

import cn.tedu.pojo.Car;
import cn.tedu.service.CarServiceImpl;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;

@RestController//接收请求
@RequestMapping("car")//规定了url和类的匹配方式
public class CarController {
    //DI依赖注入描述两个类的关系(CarServiceImpl和CarController)
    @Autowired
    private CarServiceImpl carService;

    //规定了url和方法的匹配方式,方法名不能相同,可以更精确的找到匹配的方式
    @RequestMapping("get")
    public Car get(){
        //调用的是service层返回的数据
        return carService.get();
    }
}

7、service包下创建CarService接口

作用:松耦合,面向接口开发,没有接口,代码无法整合在一起

package cn.tedu.service;

import cn.tedu.pojo.Car;
//接口里的方法都是抽象方法,都可以简写,都是public权限
public interface CarService {
    //获取汽车数据
    public abstract Car get();
}

8、service包下创建CarServiceImpl实现类

接口中有很多抽象方法,只重写你需要的方法,不需要的方法可以继续变成抽象类

package cn.tedu.service;

import cn.tedu.pojo.Car;
import org.springframework.stereotype.Service;

//实现类用来实现接口,而且可以多实现
@Service//和@component一样,ioc的功能
public class CarServiceImpl implements CarService{
    //重写规定:两同两小一大
    @Override
    public Car get() {
        Car car = new Car();
        //Lombok提供的链式编程
        car.setId(10).setType("x6").setName("BMW").setColor("red").setPrice(19.9);
        return car;
    }
}

回到CarController类中使用SpringDI依赖注入注解@Autowired建立两个类的关系

9、测试

在这里插入图片描述

 1)重新启动服务器RunApp,如果设置了热部署,就点击Build Project

2)打开网页访问服务器,服务器成功返回了数据

在这里插入图片描述

 在这里插入图片描述

  • 2
    点赞
  • 9
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值