Spring——配置,依赖注入,Bean的自动装配

3.Spring配置

3.1、别名

<!--别名,如果添加了别名,我们也可以使用别名获取到这个对象-->
<alias name="user" alias="userNew"/>

3.2、Bean的配置

<!--
    id : bean 的唯一标识符,也就是相当于我们学的对象名
    class : bean 对象所对应的全限定名 : 包名 + 类型
    name :也是别名,而且name 可以同时取多个别名
    -->
<bean id="userT" class="com.jiang.pojo.UserT" name="user2 u2,u3;u4">
    <property name="name" value="姜嘉航"/>
</bean>

3.3、import

这个import,一般用于团队开发使用,他可以将多个配置文件,导入合并为一个

假设,现在项目中有多个人开发,这三个人复制不同的类开发,不同的类需要注册在不同的bean中,我们可以利用import将所有人的beans.xml合并为一个总的!

比如现在有三个人写的xml配置文件:

  • 张三(beans.xml)

  • 李四(beans2.xml)

  • 王五(beans3.xml)

  • applicationContext.xml(总的配置文件)

    <import resource="beans.xml"/>
    <import resource="beans2.xml"/>
    <import resource="beans3.xml"/>
    

使用的时候,直接使用总的配置就行了。

4.依赖注入

4.1、构造器注入

前面IOC创建对象的方式就是构造器注入。

4.2、Set方式注入 【重点】

  • 依赖注入:Set注入!
    • 依赖:bean对象的创建依赖于容器!
    • 注入: bean对象中的所有属性,由容器来注入!

环境搭建

  1. 复杂类型(地址类)

    public class Address {
        private String address;
    
        public String getAddress() {
            return address;
        }
    
        public void setAddress(String address) {
            this.address = address;
        }
    }
    
    
  2. 真实测试对象

    package com.jiang.pojo;
    
    
    import lombok.Data;
    
    import java.util.*;
    @Data
    public class Student {
    
        private String name;
        private Address address;
        private String[] books;
        private List<String> hobbys;
        private Map<String,String> card;
        private Set<String> games;
        private String wife;
        private Properties info;// Properties文件
    }
    
  3. 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
            https://www.springframework.org/schema/beans/spring-beans.xsd">
    
        <bean id="student" class="com.jiang.pojo.Student">
            <!--第一种,普通值注入,value-->
            <property name="name" value="姜嘉航"/>
        </bean>
    
    </beans>
    
  4. 测试类

     @Test
        public void testStudent(){
            ClassPathXmlApplicationContext context = new ClassPathXmlApplicationContext("applicationContext.xml");
            Student student = (Student) context.getBean("student");
            System.out.println(student);
        }
    
  5. 完善注入信息

    <?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
            https://www.springframework.org/schema/beans/spring-beans.xsd">
        
        <bean id="address" class="com.jiang.pojo.Address">
            <property name="address" value="西安"/>
        </bean>
        
        <bean id="student" class="com.jiang.pojo.Student">
            <property name="name" value="姜嘉航"/>
            <property name="address" ref="address"/>
            <property name="books">
                <array>
                    <value>红楼梦</value>
                    <value>西游记</value>
                    <value>水浒传</value>
                    <value>三国演义</value>
                </array>
            </property>
            
            <property name="list">
                <list>
                    <value>听歌</value>
                    <value>画画</value>
                    <value>学习</value>
                </list>
            </property>
    
    
            <property name="map">
                <map>
                    <entry key="身份证" value="654646654654654654654"/>
                    <entry key="银行卡" value="6546461212654654654654654"/>
    
                </map>
            </property>
    
            <property name="set">
                <set>
                    <value>LOL</value>
                    <value>王者荣耀</value>
                    <value>魔兽世界</value>
                </set>
            </property>
    
            <property name="wife">
                <null/>
            </property>
    
            <property name="info">
                <props>
                    <prop key="driver">12121</prop>
                    <prop key="url">121212</prop>
                    <prop key="username">root</prop>
                    <prop key="password">12121</prop>
                </props>
            </property>
        </bean>
    
    </beans>
    

4.3、拓展方式注入

我们可以使用 p命令空间和c命令空间进行注入

<?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:p="http://www.springframework.org/schema/p"
       xmlns:c="http://www.springframework.org/schema/c"
       xsi:schemaLocation="http://www.springframework.org/schema/beans
        https://www.springframework.org/schema/beans/spring-beans.xsd">

    <!--p命名空间注入,可以直接注入属性的值:property-->
    <bean id="user" class="com.jiang.pojo.User" p:name="姜嘉航" p:age="23"/>

    <!--c命名空间注入,通过构造器注入:construct-args-->
    <bean id="user2" class="com.jiang.pojo.User" c:age="23" c:name="姜嘉航"/>

</beans>

测试:

@Test
public void test2(){
    ApplicationContext context = new ClassPathXmlApplicationContext("userbeans.xml");
    User user = context.getBean("user2", User.class);
    System.out.println(user);
}

注意点:p命名和c命名空间不能直接使用,需要导入xml约束!

xmlns:c="http://www.springframework.org/schema/c"
xmlns:p="http://www.springframework.org/schema/p"

5.Bean的自动装配

5.1、环境搭建

  1. User对象

    package com.jiang.entity;
    
    import lombok.Data;
    
    
    @Data
    public class User {
        private String name;
        private Cat cat;
    
        private Dog dog;
    }
    
    
  2. Cat对象

    package com.jiang.entity;
    
    public class Cat {
        private String name;
        public void shut(){
            System.out.println("miao");
        }
    
    }
    
    
  3. Dog对象

    package com.jiang.entity;
    
    public class Dog {
        private String name;
        public void shut(){
            System.out.println("wang");
        }
    
    }
    
    

5.2、ByName自动装配

<!--
    byName: 自动寻找和属性相关的bean,本质set方法,会自动匹配个bean
    -->
<bean id="people" class="com.kuang.pojo.People" autowire="byName">
    <property name="name" value="姜嘉航"/>
</bean>

5.3、ByType自动装配

    <bean id="dog" class="com.jiang.entity.Dog"/>
    <bean id="cat" class="com.jiang.entity.Cat"/>

<!--
    byType:根据这个属性的类型自动匹配,如果这个类型有多个bean就会报错
    -->
<bean id="people" class="com.jiang.entity.User" autowire="byType">
    <property name="name" value="姜嘉航"/>
</bean>

小结:

  • byname的时候,需要保证所有bean的id唯一,并且这个bean需要和自动注入的属性的set方法的值一致!
  • bytype的时候,需要保证所有bean的class唯一,并且这个bean需要和自动注入的属性的类型一致!

5.4、使用注解实现自动装配

jdk1.5支持的注解,Spring2.5就支持注解了!

The introduction of annotation-based configuration raised the question of whether this approach is “better” than XML.

要使用注解须知:

  1. 导入约束 : context约束
  2. ==配置注解的支持 :context:annotation-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"
    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">

    <context:annotation-config/>

</beans>

5.5、@Autowired

  • 直接在属性上使用即可!也可以在set方式上使用!
  • 使用Autowired 我们可以不用编写Set方法了,前提是你这个自动装配的属性在 IOC(Spring)容器中存在,且符合名字byname!

测试代码

public class People {
    //如果显示定义了Autowired的required属性为false,说明这个对象可以为null,否则不允许为空
    @Autowired(required = false)
    private Cat cat;
    @Autowired
    private Dog dog;
    private String name;
}

如果@Autowired自动装配的环境比较复杂,自动装配无法通过一个注解【@Autowired】完成的时候、我们可以使用@Qualifier(value="xxx")去配置@Autowired的使用,指定一个唯一的bean对象注入!

public class People {
    @Autowired
    @Qualifier(value="cat111")
    private Cat cat;

    @Autowired
    @Qualifier(value="dog222")
    private Dog dog;
    private String name;
}

@Resource注解

public class People {

    @Resource(name = "cat2")
    private Cat cat;

    @Resource
    private Dog dog;
    
}

@Resource 和@ Autowired 的区别:

  • 都是用来自动装配的,都可以放在属性字段上
  • @ Autowired 通过byType的方式实现,而且必须要求这个对象存在! 【常用】
  • @ Resource 默认通过byname的方式实现,如果找不到名字,则通过byType实现!如果两个都找不到的情况下,就报错! 【常用】
  • 执行顺序不同:@ Autowired 通过byType的方式实现。@ Resource 默认通过byname的方式实现。
posted @ 2020-02-23 22:14  Godlesss  阅读(146)  评论(0编辑  收藏  举报