Spring基本配置和注入配置注解使用

Spring基本配置和注入配置注解使用

一、概述

注解替换xml的方案:

常见替换:

二、实验

2.1实验Component替换Bean标签(基本配置注解,以userDao3为例)

a.写标好@Component注解

java 复制代码
package com.itheima.dao.impl;

import com.itheima.dao.UserDao;
import org.springframework.stereotype.Component;
//在注解开发中,属性只有一个,且是叫value的时候可以省略
//<bean class="com.itheima.dao.impl.UserDaoImpl3" id="userDao3"/>
@Component("userDao3")
public class UserDaoImpl3 implements UserDao {
    @Override
    public void show() {

    }
}
java 复制代码
//
// Source code recreated from a .class file by IntelliJ IDEA
// (powered by FernFlower decompiler)
//

package org.springframework.stereotype;

import java.lang.annotation.Documented;
import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;

@Target({ElementType.TYPE})
@Retention(RetentionPolicy.RUNTIME)
@Documented
@Indexed
public @interface Component {
    String value() default "";
}

将注解放在相关类的上面实际上就可以省略了全限制名,然后@Component底层又是只有一个value属性,可以是直接省略"value"了

b.配置组件扫描:

java 复制代码
<?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
       http://www.springframework.org/schema/context/spring-context.xsd
       ">

<!--加入组件扫描,扫描指定包及其子包下使用注解的类。将其放到Spring容器-->
    <context:component-scan base-package="com.itheima"/>
</beans>

测试:

java 复制代码
package com.itheima;

import org.springframework.context.support.ClassPathXmlApplicationContext;

public class ApplicationContextTest3 {

    public static void main(String[] args) {

        ClassPathXmlApplicationContext applicationContextTest2 = new ClassPathXmlApplicationContext("applicationContext3.xml");
        Object object = applicationContextTest2.getBean("userDao3");
        Object object2 = applicationContextTest2.getBean("userService3");
        System.out.println(object2);
        System.out.println( object);


    }

}

结果:

拓展:

@Component()的三个注解:

当然了,这几个标签是等价的吗,只不过我们在开发的时候遵循这个规范,见名知意。

java 复制代码
//
// Source code recreated from a .class file by IntelliJ IDEA
// (powered by FernFlower decompiler)
//

package org.springframework.stereotype;

import java.lang.annotation.Documented;
import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
import org.springframework.core.annotation.AliasFor;

@Target({ElementType.TYPE})
@Retention(RetentionPolicy.RUNTIME)
@Documented
@Component
public @interface Service {
    @AliasFor(
        annotation = Component.class
    )
    String value() default "";
}

从@Service的源码里面可以看到其本质还是 @Component(),只不过我们遵循相关的规范,一般只有在Bean不属于上面的三层的情况下我们才使用@Component()注入。

2.2其他标签(就是对应xml配置时标签的属性)

1.@Scope():

java 复制代码
//
// Source code recreated from a .class file by IntelliJ IDEA
// (powered by FernFlower decompiler)
//

package org.springframework.context.annotation;

import java.lang.annotation.Documented;
import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
import org.springframework.core.annotation.AliasFor;

@Target({ElementType.TYPE, ElementType.METHOD})
@Retention(RetentionPolicy.RUNTIME)
@Documented
public @interface Scope {
    @AliasFor("scopeName")
    String value() default "";

    @AliasFor("value")
    String scopeName() default "";

    ScopedProxyMode proxyMode() default ScopedProxyMode.DEFAULT;
}

也是只有value属性(scopeName和value是通用的,互为别名,所以默认是一个属性),直接设置为单例模式:

java 复制代码
@Scope("singleton")

2.@Lazy():

java 复制代码
//
// Source code recreated from a .class file by IntelliJ IDEA
// (powered by FernFlower decompiler)
//

package org.springframework.context.annotation;

import java.lang.annotation.Documented;
import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;

@Target({ElementType.TYPE, ElementType.METHOD, ElementType.CONSTRUCTOR, ElementType.PARAMETER, ElementType.FIELD})
@Retention(RetentionPolicy.RUNTIME)
@Documented
public @interface Lazy {
    boolean value() default true;
}

延迟加载,直接设置为true

java 复制代码
@Lazy(true)

​ 延迟加载可以实现加载完配置文件后还没有加载Bean,知道调用getBean方法时才加载Bean:

2.@PreDestroy()和destroy()

java 复制代码
 @PostConstruct
    public void init(){
            System.out.println("UserDaoImpl3对象初始化了...");
    }
    @PreDestroy
    public void destroy(){
            System.out.println("UserDaoImpl3对象销毁了...");
    }

测试:

java 复制代码
package com.itheima;

import org.springframework.context.support.ClassPathXmlApplicationContext;

public class ApplicationContextTest3 {

    public static void main(String[] args) {

        ClassPathXmlApplicationContext applicationContextTest2 = new ClassPathXmlApplicationContext("applicationContext3.xml");
        Object object = applicationContextTest2.getBean("userDao3");
        Object object2 = applicationContextTest2.getBean("userService3");
        System.out.println(object2);
        System.out.println( object);
//        要显示地关闭才会执行销毁方法,Spring容器不知道自己要挂掉了
        applicationContextTest2.close();

    }

}

结果:

2.3Spring依赖注入相关注解(注入配置)

2.3.1概述
2.3.2具体操作

1.@Value():

java 复制代码
    @Value("WangLei")
    private String username;
java 复制代码
 private String username;
@Value("WangLei")
    public void setUsername(String username) {
        this.username = username;
    }

两种方式都可以注入,上面的几个标签都是这样,就不再逐一演示了。但是说像@Value()用在法上的情形是比较少的,主要是用在Spring的框架表达式当中,例如之前我们集成Mybatis的时候注入数据库信息:

java 复制代码
jdbc.driver=com.mysql.jdbc.Driver
jdbc.url=jdbc:mysql://localhost:3306/mybatis
jdbc.username=root
jdbc.password=root
java 复制代码
@Value("${jdbc.driver}")
    private String username;

一般是这样用得多。

2.@Autowired():

java 复制代码
 @Autowired
    private UserServiceImpl3 userDao;

3.@Qualifier()

java 复制代码
    @Autowired
    @Qualifier("userDao")
    private UserDao userDao;

4.@Resource()

java 复制代码
@Resource(name = "userDao3")
    private UserDao userDao;
2.3.3@Autowired拓展

@Autowired注入在方法上时候是比配参数列表的:

java 复制代码
@Autowired
    public void xxx (UserDaoImpl3 userDao){
        System.out.println("xxx:"+userDao);
    }
@Autowired
    public void yyy(List<UserDao> userDaoList){
        System.out.println("yyy:"+userDaoList);
    }

需要UserDaoImpl3就注入UserDaoImpl3,需要UserDao集合有几个就注入几个。

Spring基本配置和注入配置注解使用

一、概述

注解替换xml的方案:

常见替换:

二、实验

2.1实验Component替换Bean标签(基本配置注解,以userDao3为例)

a.写标好@Component注解

java 复制代码
package com.itheima.dao.impl;

import com.itheima.dao.UserDao;
import org.springframework.stereotype.Component;
//在注解开发中,属性只有一个,且是叫value的时候可以省略
//<bean class="com.itheima.dao.impl.UserDaoImpl3" id="userDao3"/>
@Component("userDao3")
public class UserDaoImpl3 implements UserDao {
    @Override
    public void show() {

    }
}
java 复制代码
//
// Source code recreated from a .class file by IntelliJ IDEA
// (powered by FernFlower decompiler)
//

package org.springframework.stereotype;

import java.lang.annotation.Documented;
import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;

@Target({ElementType.TYPE})
@Retention(RetentionPolicy.RUNTIME)
@Documented
@Indexed
public @interface Component {
    String value() default "";
}

将注解放在相关类的上面实际上就可以省略了全限制名,然后@Component底层又是只有一个value属性,可以是直接省略"value"了

b.配置组件扫描:

java 复制代码
<?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
       http://www.springframework.org/schema/context/spring-context.xsd
       ">

<!--加入组件扫描,扫描指定包及其子包下使用注解的类。将其放到Spring容器-->
    <context:component-scan base-package="com.itheima"/>
</beans>

测试:

java 复制代码
package com.itheima;

import org.springframework.context.support.ClassPathXmlApplicationContext;

public class ApplicationContextTest3 {

    public static void main(String[] args) {

        ClassPathXmlApplicationContext applicationContextTest2 = new ClassPathXmlApplicationContext("applicationContext3.xml");
        Object object = applicationContextTest2.getBean("userDao3");
        Object object2 = applicationContextTest2.getBean("userService3");
        System.out.println(object2);
        System.out.println( object);


    }

}

结果:

拓展:

@Component()的三个注解:

当然了,这几个标签是等价的吗,只不过我们在开发的时候遵循这个规范,见名知意。

java 复制代码
//
// Source code recreated from a .class file by IntelliJ IDEA
// (powered by FernFlower decompiler)
//

package org.springframework.stereotype;

import java.lang.annotation.Documented;
import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
import org.springframework.core.annotation.AliasFor;

@Target({ElementType.TYPE})
@Retention(RetentionPolicy.RUNTIME)
@Documented
@Component
public @interface Service {
    @AliasFor(
        annotation = Component.class
    )
    String value() default "";
}

从@Service的源码里面可以看到其本质还是 @Component(),只不过我们遵循相关的规范,一般只有在Bean不属于上面的三层的情况下我们才使用@Component()注入。

2.2其他标签(就是对应xml配置时标签的属性)

1.@Scope():

java 复制代码
//
// Source code recreated from a .class file by IntelliJ IDEA
// (powered by FernFlower decompiler)
//

package org.springframework.context.annotation;

import java.lang.annotation.Documented;
import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
import org.springframework.core.annotation.AliasFor;

@Target({ElementType.TYPE, ElementType.METHOD})
@Retention(RetentionPolicy.RUNTIME)
@Documented
public @interface Scope {
    @AliasFor("scopeName")
    String value() default "";

    @AliasFor("value")
    String scopeName() default "";

    ScopedProxyMode proxyMode() default ScopedProxyMode.DEFAULT;
}

也是只有value属性(scopeName和value是通用的,互为别名,所以默认是一个属性),直接设置为单例模式:

java 复制代码
@Scope("singleton")

2.@Lazy():

java 复制代码
//
// Source code recreated from a .class file by IntelliJ IDEA
// (powered by FernFlower decompiler)
//

package org.springframework.context.annotation;

import java.lang.annotation.Documented;
import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;

@Target({ElementType.TYPE, ElementType.METHOD, ElementType.CONSTRUCTOR, ElementType.PARAMETER, ElementType.FIELD})
@Retention(RetentionPolicy.RUNTIME)
@Documented
public @interface Lazy {
    boolean value() default true;
}

延迟加载,直接设置为true

java 复制代码
@Lazy(true)

​ 延迟加载可以实现加载完配置文件后还没有加载Bean,知道调用getBean方法时才加载Bean:

2.@PreDestroy()和destroy()

java 复制代码
 @PostConstruct
    public void init(){
            System.out.println("UserDaoImpl3对象初始化了...");
    }
    @PreDestroy
    public void destroy(){
            System.out.println("UserDaoImpl3对象销毁了...");
    }

测试:

java 复制代码
package com.itheima;

import org.springframework.context.support.ClassPathXmlApplicationContext;

public class ApplicationContextTest3 {

    public static void main(String[] args) {

        ClassPathXmlApplicationContext applicationContextTest2 = new ClassPathXmlApplicationContext("applicationContext3.xml");
        Object object = applicationContextTest2.getBean("userDao3");
        Object object2 = applicationContextTest2.getBean("userService3");
        System.out.println(object2);
        System.out.println( object);
//        要显示地关闭才会执行销毁方法,Spring容器不知道自己要挂掉了
        applicationContextTest2.close();

    }

}

结果:

2.3Spring依赖注入相关注解(注入配置)

2.3.1概述
2.3.2具体操作

1.@Value():

java 复制代码
    @Value("WangLei")
    private String username;
java 复制代码
 private String username;
@Value("WangLei")
    public void setUsername(String username) {
        this.username = username;
    }

两种方式都可以注入,上面的几个标签都是这样,就不再逐一演示了。但是说像@Value()用在法上的情形是比较少的,主要是用在Spring的框架表达式当中,例如之前我们集成Mybatis的时候注入数据库信息:

java 复制代码
jdbc.driver=com.mysql.jdbc.Driver
jdbc.url=jdbc:mysql://localhost:3306/mybatis
jdbc.username=root
jdbc.password=root
java 复制代码
@Value("${jdbc.driver}")
    private String username;

一般是这样用得多。

2.@Autowired():

java 复制代码
 @Autowired
    private UserServiceImpl3 userDao;

3.@Qualifier()

java 复制代码
    @Autowired
    @Qualifier("userDao")
    private UserDao userDao;

4.@Resource()

java 复制代码
@Resource(name = "userDao3")
    private UserDao userDao;
2.3.3@Autowired拓展

@Autowired注入在方法上时候是比配参数列表的:

java 复制代码
@Autowired
    public void xxx (UserDaoImpl3 userDao){
        System.out.println("xxx:"+userDao);
    }
@Autowired
    public void yyy(List<UserDao> userDaoList){
        System.out.println("yyy:"+userDaoList);
    }

需要UserDaoImpl3就注入UserDaoImpl3,需要UserDao集合有几个就注入几个。

相关推荐
yaoxin5211231 分钟前
470. Java 反射 - Member 接口与 AccessFlag
java·开发语言·python
做个文艺程序员18 分钟前
Linux第24篇:Java应用监控体系搭建:Prometheus+Grafana可视化运维
java·grafana·prometheus
FF2501_940228581 小时前
Grid 构建月历网格:7 列模板 + 日期占位算法
后端·华为·harmonyos·鸿蒙系统
神奇小汤圆1 小时前
线程池的 DiscardPolicy 为什么是「静默杀手」?一个生产事故的完整复盘
后端
大鸡腿同学1 小时前
个人博主 AI 剪辑实操:口播视频 3 步出片,省 80% 剪辑时间
后端
小钻风33661 小时前
Spring Boot 文件上传详解:深入理解 MultipartFile 的使用与原理
java·开发语言
其美杰布-富贵-李1 小时前
Spring Boot 工程开发全流程说明
java·spring boot·后端
xianjixiance_1 小时前
HarmonyOS应用开发实战:萌宠日记 - 整体架构设计与技术选型解析
后端
掘金者阿豪1 小时前
数据库优化器到底在想什么:一个SQL今天能跑明天崩的背后
后端
b130538100492 小时前
HarmonyOS应用开发实战:萌宠日记 - 回调函数模式
后端