Spring-依赖注入(DI)相关

Spring-依赖注入(DI)相关

  • 思考:

    • 1.向一个类中传递数据的方式有几种?

      • set方法
      • 构造方法
    • 2.依赖注入(DI)描述了在容器中建立bean与bean之间依赖关系的过程,如果bean运行需要的是数字或者字符串呢?

      • 引用类型
      • 简单类型:基本数据类型和String

一、依赖注入的方式

setter注入构造器注入
简单类型简单类型
引用类型引用类型

1.1 setter注入 – 引用类型

  • (1)OrderDaoImpl类中,依赖UserDao和BookDao

    /**
     * @author: sea
     * @date: 2023/6/25 15:25
     */
    public class OrderDaoImpl implements OrderDao {
        private UserDao userDao;
        private BookDao bookDao;
        @Override
        public void save() {
            System.out.println("Order saving ... ");
            userDao.save();
            bookDao.save();
        }
        public void setUserDao(UserDao userDao) {
            this.userDao = userDao;
        }
    
        public void setBookDao(BookDao bookDao) {
            this.bookDao = bookDao;
        }
    }
    
  • (2)配置文件中配置bean和各个bean之间的依赖关系注入**【property标签的ref属性注入】**

    <bean id="userDao" class="com.sea.dao.impl.UserDaoImpl"/>
    <bean id="bookDao" class="com.sea.dao.impl.BookDaoImpl"/>
    
    <bean id="orderDao" class="com.sea.dao.impl.OrderDaoImpl">
        <property name="userDao" ref="userDao" />
        <property name="bookDao" ref="bookDao" />
    </bean>
    
  • (3)获取Spring容器中管理的bean,并调用相关方法

    /**
     * @author: sea
     * @date: 2023/6/30 15:37
     */
    public class AppForDISetter {
        public static void main(String[] args) {
            ApplicationContext context = new ClassPathXmlApplicationContext("applicationContext.xml");
            OrderDao orderDao = (OrderDao) context.getBean("orderDao");
    
            orderDao.save();
        }
    }
    

1.2 setter注入 – 简单类型

  • (1)UserDaoImpl类中,依赖两个简单类型:int和String

    /**
     * @author: sea
     * @date: 2023/6/25 15:26
     */
    public class UserDaoImpl implements UserDao {
        private int id;
        private String name;
        @Override
        public void save() {
            System.out.println("UserDao saving ... ");
            System.out.println("==== " + this.id + " ==== " + this.name);
        }
    
        public void setId(int id) {
            this.id = id;
        }
    
        public void setName(String name) {
            this.name = name;
        }
    }
    
    
  • (2)配置文件中配置bean和简单类型注入**【property标签的value属性注入】**

    <bean id="userDao" class="com.sea.dao.impl.UserDaoImpl">
        <property name="id" value="1"/>
        <property name="name" value="sea"/>
    </bean>
    
  • (3)获取Spring容器中管理的bean,并调用相关方法

    /**
     * @author: sea
     * @date: 2023/6/30 15:37
     */
    public class AppForDISetter {
        public static void main(String[] args) {
            ApplicationContext context = new ClassPathXmlApplicationContext("applicationContext.xml");
            UserDao userDao = (userDao) context.getBean("userDao");
    
            userDao.save();
        }
    }
    

1.3 构造器注入

  • (1)BookDaoImpl类和UserDaoImpl类,其中UserDaoImpl依赖两个简单类型:int和String

    /**
     * @author: sea
     * @date: 2023/6/25 15:25
     */
    public class BookDaoImpl implements BookDao {
    
        private BookDaoImpl() {//此处私有的构造方法也可以找到【反射机制】
    
        }
    
        public void save() {
            System.out.println("Bookdao saving ... ");
        }
    }
    
    /**
     * @author: sea
     * @date: 2023/6/25 15:26
     */
    public class UserDaoImpl implements UserDao {
        private int id;
        private String name;
    
        public UserDaoImpl(int id, String name) {
            this.id = id;
            this.name = name;
        }
    
        @Override
        public void save() {
            System.out.println("UserDao saving ... ");
            System.out.println("==== " + this.id + " ==== " + this.name);
        }
    }
    
  • (2)BookServiceImpl类,该类依赖BookDao和UserDao两个Dao类,并**【通过构造器进行注入】**

    /**
     * @author: sea
     * @date: 2023/6/30 16:12
     */
    public class BookServiceImpl implements BookService {
        BookDao bookDao;
        UserDao userDao;
    
        public BookServiceImpl(BookDao bookDao, UserDao userDao) {
            this.bookDao = bookDao;
            this.userDao = userDao;
        }
    
        @Override
        public void save() {
            System.out.println("bookService saving ...");
            bookDao.save();
            userDao.save();
        }
    }
    
  • (3)配置文件中配置bean,以及相关的依赖注入**【通过constructor-arg标签进行注入】**

        <bean id="bookDao" class="com.sea.dao.impl.BookDaoImpl"/>
        <bean id="userDao" class="com.sea.dao.impl.UserDaoImpl">
            <constructor-arg name="id" value="1"/>
            <constructor-arg name="name" value="sea"/>
        </bean>
    
        <bean id="bookService" class="com.sea.service.impl.BookServiceImpl">
            <constructor-arg name="bookDao" ref="bookDao"/>
            <constructor-arg name="userDao" ref="userDao"/>
        </bean>
    
  • (4)获取Spring容器中管理的bean,并调用相关方法

    /**
     * @author: sea
     * @date: 2023/6/30 15:37
     */
    public class AppForConstructor {
        public static void main(String[] args) {
            ApplicationContext context = new ClassPathXmlApplicationContext("applicationContext.xml");
            BookService bookService = (BookService) context.getBean("bookService");
            bookService.save();
        }
    }
    

1.4 两种注入方式选择

  • 使用构造器方式注入:
    • 1.强制依赖
    • 2.Spring框架建议使用构造器,比较严谨
  • 使用setter方式注入:
    • 1.可选依赖
    • 2.自己开发的模块推荐setter注入
  • 【可能管理的类没有提供构造器,因此,根据实际开发情况选择!】
  • 目前存在的弊端:还是得自己手动配置!!因此,引入自动装配的概念!

二、依赖自动装配

2.1 概念

  • **IoC容器 **根据bean所依赖的资源在容器中 **自动查找并注入 **到bean中的过程称为 自动装配

2.2 自动装配的方式

  • 按类型(常用)
  • 按名称
  • 按构造方法
  • 不启用自动装配

2.3 实现

  • 在配置文件中,使用bean标签的autowire设置自动装配的方式;

    Spring_自动装配的类型_1

  • 其中:

    • 自动装配仅适用于引用类型装配;
    • 按类型装配:需要保证相同类型的bean只能有一个;
    • 按名称装配:需要保证bean的id属性与变量名一致,即变量名称与配置产生耦合,不推荐使用
    • 自动装配优先级低于setter注入与构造器注入,同时使用时,自动装配配置失效。

三、集合注入

  • 集合:

    • 数组
    • List
    • Set
    • Map
    • Properties
  • 注入方式:

    <?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="bookDao" class="com.sea.dao.impl.BookDaoImpl">
            <property name="arr">
                <array>
                    <value>1</value>
                    <value>2</value>
                    <value>3</value>
                    <value>4</value>
                    <value>5</value>
                </array>
            </property>
            <property name="list">
                <list>
                    <value>a</value>
                    <value>b</value>
                    <value>c</value>
                    <value>d</value>
                    <value>e</value>
                </list>
            </property>
            <property name="map">
                <map>
                    <entry key="1" value="a"/>
                    <entry key="2" value="b"/>
                    <entry key="3" value="c"/>
                    <entry key="4" value="d"/>
                    <entry key="5" value="e"/>
                </map>
            </property>
            <property name="set">
                <set>
                    <value>a</value>
                    <value>b</value>
                    <value>c</value>
                    <value>d</value>
                    <value>e</value>
                </set>
            </property>
            <property name="properties">
                <props>
                    <prop key="driver">com.mysql.jdbc.Driver</prop>
                    <prop key="url">jdbc:mysql://localhost:3306/test</prop>
                    <prop key="username">root</prop>
                    <prop key="password">123456</prop>
                </props>
            </property>
        </bean>
    
        <bean id="bookService" class="com.sea.service.impl.BookServiceImpl">
            <constructor-arg name="bookDao" ref="bookDao"/>
        </bean>
    </beans>
    
    • 注入的值可以是基本数据类型,也可以是引用类型。

四、案例:数据源对象管理

  • 以配置数据库连接池为例:

    <!--  druid连接池  -->
    <bean id="dataSource_druid" class="com.alibaba.druid.pool.DruidDataSource">
        <property name="driverClassName" value="com.mysql.jdbc.Driver"/>
        <property name="url" value="jdbc:mysql://localhost:3306/springdb"/>
        <property name="username" value="root"/>
        <property name="password" value="123456"/>
    </bean>
    
    <!--  c3p0连接池  -->
    <bean id="dataSource_c3p0" class="com.mchange.v2.c3p0.ComboPooledDataSource">
        <property name="driverClass" value="com.mysql.jdbc.Driver"/>
        <property name="jdbcUrl" value="jdbc:mysql://localhost:3306/springdb"/>
        <property name="user" value="root"/>
        <property name="password" value="123456"/>
        <property name="maxPoolSize" value="1000"/>
    </bean>
    
  • 如果需要从配置文件中读取配置:

    • 1.开启一个新的命名空间
    <?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"
           
            >
      
      ......
      
    </beans>
    

    Spring_数据源对象管理_1

    • 2.使用context空间加载properties文件
    • 3.使用属性占位符 ${} 读取properties文件中的值
    <!--  1.开启contex命名空间  -->
        
    <!--  2.使用context空间加载properties文件  -->
    <context:property-placeholder location="mysql.properties"/>
    <!--  3.使用属性占位符 ${} 读取properties文件中的值  -->
    <!--  druid连接池  -->
    <bean id="dataSource_druid" class="com.alibaba.druid.pool.DruidDataSource">
        <property name="driverClassName" value="${driver}"/>
        <property name="url" value="${url}"/>
        <property name="username" value="${user}"/>
        <property name="password" value="${password}"/>
    </bean>
    
    • mysql.properties配置文件如下:

      driver=com.mysql.jdbc.Driver
      url=jdbc:mysql://localhost:3306/springdb
      username=root
      password=123456
      
      • 此处username可能会与系统的环境变量冲突,系统的环境变量优先级高,因此可能输出的username不是配置文件中的值。解决:

        <!--  增加属性 system-properties-mode="NEVER" 即可 -->
        
        <!--  2.使用context空间加载properties文件  -->
        <context:property-placeholder location="mysql.properties" system-properties-mode="NEVER"/>
        
      • 要读取多个配置文件:

        • 读取当前工程目录下所有的properties文件。【标准格式
        <context:property-placeholder location="classpath:*.properties" system-properties-mode="NEVER"/>
        
        • 读取当前工程目录下所有的properties文件以及依赖的外部jar包中的properties文件。
        <context:property-placeholder location="classpath*:*.properties" system-properties-mode="NEVER"/>
        
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

打赏作者

SEA-365

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

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

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

打赏作者

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

抵扣说明:

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

余额充值