赞
踩
1.在Spring中的两个个重要概念一个是IoC,一个是bean;bean是Spring IoC实例化、管理、装配的对象,那么Spring IoC如何管理bean呢?答案是:基于xml管理bean和基于注解管理bean。
1. 配置pom.xml文件
2. 创建pojo实体类
3. 创建配置文件applicationContext.xml
<bean id="hellospring" class="com.gz.pojo.HelloWorld"></bean>
* bean:配置一个bean对象,将对象交给IOC容器管理
* Spring提供的对象默认是单例的,一个bean提供一个对象
* 包含的属性:
* id:bean的唯一标识,不能重复
* class:设置bean对象所对应的类型(只能为类,不能为接口)
4. 进行测试
1. 获取IOC容器
2. 获取IOC容器中的bean对象
- @Test
- public void testHelloWorld(){
- //1.获取IOC容器:使用ApplicationContext的子类:ClassPathXmlApplicationContext
- ClassPathXmlApplicationContext ioc = new
- ClassPathXmlApplicationContext("applicationContext.xml");
- //2.获取IOC容器中的bean对象:使用getBean()方法
- HelloWorld helloworld = (HelloWorld) ioc.getBean("hellospring");
- //调用该类中的方法
- helloworld.sayHello();
- }
1.在Spring框架的搭建过程中,一个重点是要创建配置文件applicationContext.xml,在applicationContext.xml中创建bean对象,设置bean对象的id和class为后续获取bean对象做好准备。这就是xml文件的作用之一。
2.xml配置文件的其他作用:
进行依赖注入
进行自动装配
依赖注入:为当前的类的属性赋值;有两种方法进行依赖注入:
* setter注入
* 标签:property:通过成员变量的set方法进行封装
* name:设置需要赋值的属性名(和set方法有关)
* value:设置为属性所赋的值
- <bean id="studentOne" class="com.gz.spring.pojo.Student">
- <property name="id" value="1001"></property>
- <property name="name" value="李四"></property>
- <property name="age" value="11"></property>
- <property name="gender" value="1"></property>
- </bean>
* 构造器注入
* 标签:constructor-arg
* 注意:value值应与有参构造器相对应;
* 若存在两个相同参数的构造器时,可以通过属性来匹配指定的有参构造器
- <bean id="studentFour" class="com.gz.spring.pojo.Student">
- <constructor-arg value="1004"></constructor-arg>
- <constructor-arg value="赵四"/>
- <constructor-arg value="14"></constructor-arg>
- <constructor-arg value="男"></constructor-arg>
- </bean>
* 特殊值处理
1. 字面量赋值(字面量:包装类/String)
* value中的值就是给字面量赋的值
2. null赋值:不能用value=null赋值,而是在当前property里面设置null标签
- <bean id="studentFive" class="com.gz.spring.pojo.Student">
- <property name="id">
- <null />
- </property>
- </bean>
* 存在问题: < 在xml文档中用来定义标签的开始,不能随便使用
3. 第一种方法:xml赋值
* 使用xml实体代替:
* < 表示 < > 表示 >
- <bean id="studentSix" class="com.gz.spring.pojo.Student">
- <property name="name" value="a < b"></property>
- </bean>
第二种方法:CDATA节
* CDATA节中C表示character是文本字符的意思,CDATA表示纯文本数据;xml中看到CDATA节就知道为纯文本,在CDATA节中写什么都可以
- <bean id="studentSeven" class="com.gz.spring.pojo.Student">
- <property name="name">
- <value><![CDATA[ a < b ]]></value>
- </property>
- </bean>
* 注意:自动装配时只能将实现类写入bean的class中,不能写接口;并且配置文件中是通过set方法为类的成员变量赋值的
* 自动装配的概念:根据指定的策略,在IOC容器中匹配某一个bean,自动为指定的bean所依赖的类类型或接口类型属性赋值
* 三层业务架构:控制层中调用service处理业务逻辑,service中调用dao实现持久化操作(注意,调用过程中要实现set方法,因为自动装配底层使用的是set方法进行赋值)
* 自动装配的策略:通过bean标签中对autowire设置
* no、defalut:表示不装配,即bean中的属性不会自动匹配某个bean为属性赋值。此时属性使用默认值
* byType:根据类型自动为当前属性匹配到某一个bean赋值(用得多)
* 注意:当使用byType实现自动装配时,IOC容器中有且只有一个类型匹配的bean能够为属性赋值
* 若通过类型未找到任何一个bean,此时不装配使用默认值
* 若通过类型找到多个bean、此时报错:NoUniqueBean
* byName(用得少):btType不行的时候用;将要赋值的属性的属性名作为bean的id在IOC容器中匹配某个bean,为属性赋值
* 当类型匹配的bean有多个时,此时可以使用byName实现自动装配
* 基于xml的自动装配用的并不多,一般用得多的是基于注解的自动装配
* 这是因为基于xml的自动装配是对于所有的属性进行的,无法对其中某些属性单独赋值。而基于注解的自动装配,可以只为加上注解的成员变量进行自动装配
- <!--
- 基于xml进行自动装配的步骤:
- 1.存在一个目标接口和目标实现类
- 注意:调用类时需要实现set方法,因此基于xml的ioc管理bean是通过set方法进行依赖注入的
- 2.在bean标签中的autowire属性进行设置
- a>byType:通过类型进行自动装配
- b>byName:通过属性名进行自动装配
- -->
-
- <bean id="userController" class="com.gz.spring.controller.UserController" autowire="byType"></bean>
-
- <bean id="userService" class="com.gz.spring.service.impl.UserServiceImpl" autowire="byType"></bean>
-
- <bean id="userDao" class="com.gz.spring.dao.impl.UserDaoImpl"></bean>
-
- </beans>
和xml配置文件一样,注解本身并不能执行,注解本身仅仅只是做一个标记,具体的功能是框架检测到注解标记的位置,然后针对这个位置按照注解标记的功能执行具体操作。
* 本质上来说,所有的操作都是Java代码完成的,xml和注解只是告诉框架的Java代码如何执行
Spring为了知道程序员在哪些地方标记了什么注解,需要通过扫描的方式进行检测,然后根据注解进行后续操作。
- <!-- 扫描组件-->
- <context:component-scan base-package="com.gz.spring.annotation">
- </context:component-scan>
- 注意:注解要加到实现类上
* @Component:将类标识为普通组件
* @Controller:将类标识为控制层组件
* @Service:将类标识为业务层组件
* @Repository:将类标识为持久层组件
* 四个注解功能一样,只是名字不一样,这是为了开发人员看的
Spring和Spring MVC是放在一起使用的,Spring MVC需要扫描的是控制层,Spring需要扫描的是除控制层以外所有的组件。这该如何实现呢?
* 在context中使用exclude- filter,排除扫描(用得多)
* type:设置排除扫描的方式
* annotation:根据注解的类型进行排除;在expression中设置排除的注解的全类名
* assignable:根据类的类型进行排除;在expression中设置排除的类的全类名
- <!-- 使用排除扫描-->
- <context:component-scan base-package="com.gz.spring">
- <!-- type:排除扫描的方式
- annotation:根据注解类型排除
- assignable:根据类的类型排除
- -->
- <context:exclude-filter type="annotation" expression="org.springframework.stereotype.Controller"></context:exclude-filter>
- <context:exclude-filter type="assignable" expression="com.gz.spring.controller.UserController"></context:exclude-filter>
- </context:component-scan>
* 在context中使用include-context:包含扫描(用的不多)
* 注意:需要在context:component-scan标签中设置use-defalut-filters为false;即取消默认的扫描所有类功能,此时才可以使用包含扫描
* 当use-defalut-filters为true(默认)时,可以使用排除扫描
* type与上相同
* 通过注解+扫描所配置的bean的id,默认值为类的小驼峰:类名的首字母为小写的结果
* 自定义设置bean的id:可以通过标识组件的注解的value属性值设置
- @Controller("controller")
- public class UserController {
- }
* 步骤如下:
* 第一步:类上要写上相对应的注解,以便扫描
* 第二步:在成员变量上标记@Autowired注解即可完成自动装配,不需要再提供set方法(在项目中也如此用)
- <!--
- 基于注解管理bean步骤:
- 1.在映射文件中填写好扫描组件(固定的,记住)
- 2.将不同实现类对应的注解加入到类上:为了扫描,以便ioc容器进行管理
- 3.在成员变量上标记@Autowired注解,不需要再提供set方法
- -->
- <!-- 1.扫描组件-->
- <cotext:component-scan base-package="com.gz.spring"></cotext:component-scan>
- //2.将实现类标记为相应标签,以便ioc容器扫描(可以不用在像xml一样写bean)
- @Service
- public class UserServiceImpl implements UserService {
-
- //3.在成员变量上标记@AutoWired注解,而不再需要提供set方法
- @Autowired
- private UserDao userDao;
-
- public void setUserDao(UserDao userDao) {
- this.userDao = userDao;
- }
-
- @Override
- public void saveUser() {
- userDao.saveUser();
- }
- }
1. @Autowired:实现自动装配功能的注解
2. @Autowired注解其他能够标识的位置
* 标识在成员变量上,此时不需要设置成员变量的set方法(一般用这个,此时可以不用在创造set方法)
* 标识在set方法上
* 标识在为当前成员变量赋值的有参构造器上
3. @Autowired注解的原理
1. 默认通过byType方式,在ioc容器中通过类型匹配某个bean为属性赋值(一般都是这这个就可以)
2. 若有多个类型匹配的bean,此时会自动转换为byName的方式实现自动装配的效果;即将要赋值的属性的属性名作为bean的id匹配某个bean为属性赋值
3. 若byType和byName的方式都无法实现自动装配,即IOC容器中有多个类型匹配的bean,且这些bean的id和要赋值的属性的属性名都不一致,此时会抛出异常:
NoUniqueBeanDefinitionException
(这种情况几乎不会发生,一般默认byType就能处理,因为一个类型的bean不会在ioc容器中存在多个)
4. 若出现以上情况则可以在要赋值的属性上,添加一个注解@Qualifier;通过该注解的value属性值,指定某个bean的ID,将这个bean为属性赋值
4. 若ioc容器中没有任何一个类型匹配的bean,此时抛出异常:noSucnBean;
* 这是因为在@Autowired注解中有一个属性required,默认值为true,要求必须完成自动装配;
* 若将required设置为false,此时能装配则装配,无法装配则使用属性的默认值
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。