简析SpringIOC扫描器的使用配置原理

1、本篇博客的背景和目的

目前我本人正在学习SpringFramework的知识,这也是这个专栏的主题。我前面的几篇博文中,简单的认识了一下SpringFramework,记录了SpringFramework的环境搭建,记录了SpringIOC如何加载配置文件,记录了SpringIOC三种Bean对象的实例化方法。还记录了SpringIOC手动装配(注入)的方法之一:set方法注入。还有另外三个不太常用的SpringIOC手动注入的方法。其实目前大部分都使用的是自动注入的方法,手动注入使用的不多。就算是使用手动注入的方法,使用的主流也是:set方法注入。自动注入的方法主要是使用两个注解,@Autowired注解或者是@Resource注解。上面两篇博客我都记录到了。本篇博客我记录一下如何使用SpringIOC扫描器。

2、我的上一篇博客

我的上一篇博客记录的是Spring中使用自动注入的其中一种方式:使用@Autowired注解。链接如下所示:

SpringIOC自动注入:@Autowired注解注入_你是我的日月星河的博客-CSDN博客icon-default.png?t=M4ADhttps://blog.csdn.net/weixin_46281472/article/details/125153777?spm=1001.2014.3001.5502

3、为什么要使用SpringIOC扫描器呢?

其实这么说吧,人类无论发明任何的技术,很多情况下的主要目的就是 懒!!为了能够更省力的做好某一件事情,才发明出来了某种技术或者说是方法。

使用SpringIOC扫描器也是一样的道理。我这里先粘贴一张图片:

也就是我们的Bean很多的话,每一个实体类我们都要写一个bean标签,这很麻烦的;无论手动注入还是自动注入,都是需要写bean标签的;那么我们可不可以不写Bean标签呢?也就是少些XML配置文件呢?

4、SpringIOC扫描器的简单配置思想

上图中的意思,简单通俗说:我们在类上面使用@Repository注解,@Service注解,@Controller注解或者是@Component注解就可以代替对应XML文件中的bean标签了。但是,有一点需要注意的是:即使我们写了这些标签,如果没有在XML文件中配置扫描器的话,是没有用的,即这些实体类不会交给SpringIOC管理而被自动实例化。所以需要在XML文件中写上某一个标签配置好扫描器。

上面图中有一点需要注意的是:使用扫描器的方式,默认bean标签的id属性值是类的首字母小写以后的字符串。这一点需要我们在Main方法中获取实例化对象的时候使用到。

5、明确一下代码的文件结构

结构如下所示:

文件的结构读者注意文件夹的结构就可以,至于里面的类,我下面会记录到的。 

6、我本人的示例代码

POM文件代码如下:

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

  <groupId>com.dcy</groupId>
  <artifactId>spring04</artifactId>
  <version>1.0-SNAPSHOT</version>

  <name>spring04</name>
  <!-- FIXME change it to the project's website -->
  <url>http://www.example.com</url>

  <properties>
    <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
    <maven.compiler.source>11</maven.compiler.source>
    <maven.compiler.target>11</maven.compiler.target>
  </properties>

  <dependencies>

<!--    这个是Spring框架的核心依赖-->
    <dependency>
      <groupId>org.springframework</groupId>
      <artifactId>spring-context</artifactId>
      <version>5.2.12.RELEASE</version>
    </dependency>

    <dependency>
      <groupId>junit</groupId>
      <artifactId>junit</artifactId>
      <version>4.11</version>
      <scope>test</scope>
    </dependency>

  </dependencies>

  <build>
    <pluginManagement><!-- lock down plugins versions to avoid using Maven defaults (may be moved to parent pom) -->
      <plugins>
        <!-- clean lifecycle, see https://maven.apache.org/ref/current/maven-core/lifecycles.html#clean_Lifecycle -->
        <plugin>
          <artifactId>maven-clean-plugin</artifactId>
          <version>3.1.0</version>
        </plugin>
        <!-- default lifecycle, jar packaging: see https://maven.apache.org/ref/current/maven-core/default-bindings.html#Plugin_bindings_for_jar_packaging -->
        <plugin>
          <artifactId>maven-resources-plugin</artifactId>
          <version>3.0.2</version>
        </plugin>
        <plugin>
          <artifactId>maven-compiler-plugin</artifactId>
          <version>3.8.0</version>
        </plugin>
        <plugin>
          <artifactId>maven-surefire-plugin</artifactId>
          <version>2.22.1</version>
        </plugin>
        <plugin>
          <artifactId>maven-jar-plugin</artifactId>
          <version>3.0.2</version>
        </plugin>
        <plugin>
          <artifactId>maven-install-plugin</artifactId>
          <version>2.5.2</version>
        </plugin>
        <plugin>
          <artifactId>maven-deploy-plugin</artifactId>
          <version>2.8.2</version>
        </plugin>
        <!-- site lifecycle, see https://maven.apache.org/ref/current/maven-core/lifecycles.html#site_Lifecycle -->
        <plugin>
          <artifactId>maven-site-plugin</artifactId>
          <version>3.7.1</version>
        </plugin>
        <plugin>
          <artifactId>maven-project-info-reports-plugin</artifactId>
          <version>3.0.0</version>
        </plugin>
      </plugins>
    </pluginManagement>
  </build>
</project>

上面是我的POM文件的代码。我创建项目的时候使用了一个模板,所以多出来了很多的插件。其实读者可以直接创建一个空的Maven项目。我使用的JDK版本是JDK11。上面POM文件里面最主要的就是依赖,一个是SpringFramework的核心依赖,另一个是和测试有关的依赖junit。

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"
       xmlns:context="http://www.springframework.org/schema/context"
       xsi:schemaLocation="http://www.springframework.org/schema/beans
        https://www.springframework.org/schema/beans/spring-beans.xsd
        http://www.springframework.org/schema/context
        https://www.springframework.org/schema/context/spring-context.xsd">
    <!--   开启自动化装备(注入),也就是注解注入 @Autowired或者@Resource-->
    <!--    好处就是我们不需要在手动写  property标签,不需要使用set方法或者是构造器方法
        去手动写类里面的参数关系
-->
    <context:annotation-config/>
<!--    开启SpringIOC的自动扫描,设置扫描包的范围 一般都是根目录范围下的所有
     这个时候我们就可以使用 @Controller,@Service注解了
    此时还没有在Main方法的类上面使用  @SpringBootApplication注解
-->
    <context:component-scan base-package="com.dcy"></context:component-scan>
</beans>

在上面的XML文件中,首先就是文件头,这个就不需要多说了,是不能错的,没有这些文件头,里面的标签没有提示并且不起作用。然后是context:annotation-config标签,用来开启自动注入;context:component-scan标签用于开启配置扫描器,其中的base-package属性的值是扫描的范围。代码里面扫描的范围是:com.dcy下面的所有类。

这里多说一下:我们一般设置的扫描范围都是com.xxx 就这样就可以了,因为上一级目录就是java了。就是扫描这个包下面的所有类,当然啦,这些类需要有@Controller这样的注解;扫描以后,都是单例扫描的,每次拿到的都是同一个对象(这个我其实说过至少是第三次了!)。这样有些就不能被扫描到,比如User类,登录的用户不一样,怎么能使用SpringIOC 自动注入的单例模式呢?

AccountController类代码如下所示:

package com.dcy.controller;

import com.dcy.service.AccountService;
import org.springframework.stereotype.Controller;

import javax.annotation.Resource;

@Controller
public class AccountController {

    @Resource
    private AccountService accountService;

    public void test(){
        System.out.println("这个是AccountController");
        accountService.test();
    }
}

我们上面的代码中,在AccountController类的上方放置了@Controller注解,并且我们已经在XML配置文件里面配置扫描器,且:AccountController类所在的位置也位于扫描器的范围内。然后我们在类里面注入了AccountService类,在这个类的上面使用了@Resource(来自于JAVA)注解实现自动注入。这样使用的正确性在于:我们已经在XML文件里面开启了使用注解自动注入功能,并且还应该满足AccountService类在XML文件里面有对应的bean标签或者开启扫描器的情况下AccountService类上方有@Service类似的注解,即:AccountService类已经交给了SpringIOC管理并实例化。

上面的一段话有点绕口,但我认为讲解的还是比较清楚的,读者可以仔细理解一下

AccountService类代码如下所示:

package com.dcy.service;

import com.dcy.dao.AccountDao;
import org.springframework.stereotype.Service;

import javax.annotation.Resource;

@Service
public class AccountService {

    @Resource
    private AccountDao accountDao;

    public void test(){
        System.out.println("AccountService");
        accountDao.test();
    }
}

 上面的代码逻辑其实跟AccountController类的代码逻辑是一样的,这里我就不多解释了。

AccountDao类代码如下所示:

package com.dcy.dao;

import org.springframework.stereotype.Repository;

@Repository
public class AccountDao {

    public void test(){
        System.out.println("AccountDao");
    }
}

Main方法测试代码如下所示:

package com.dcy;

import com.dcy.controller.AccountController;
import org.springframework.context.ApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;

public class Starter {
    public static void main(String[] args) {
        //首先加载配置文件
        ApplicationContext ac=new ClassPathXmlApplicationContext("spring03.xml");
        //获得UserService对象
        AccountController accountController = (AccountController) ac.getBean("accountController");
        //调用方法
        accountController.test();
    }
}

代码我就不多解释了,运行结果如下所示:

到此为止就是全部的实例代码,暂时也没有什么需要补充的了。 

7、我的下一篇博文 

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

你是我的日月星河

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值