对于学习spring有帮助的站点:http://jinnianshilongnian.iteye.com/blog/1482071

Bean的自己主动装配

Spring IOC 容器能够自己主动装配 Bean. 需要做的仅仅是在 的 autowire 属性里指定自己主动装配的模式

有以下几种自己主动装配的类型:

  • byType(依据类型自己主动装配): 若 IOC 容器中有多个与目标 Bean 类型一致的 Bean. 在这样的情况下, Spring

    将无法判定哪个 Bean 最合适该属性, 所以不能执行自己主动装配.
  • byName(依据名称自己主动装配): 必须将目标 Bean 的名称和属性名设置的全然同样.
  • constructor(通过构造器自己主动装配): 当 Bean 中存在多个构造器时, 此种自己主动装配方式将会非常复杂. 不推荐使用

首先我们先来看一个手动装配的样例,

文件夹结构

先创建两个实体Bean

  1. package com.gp.spring.autowire;
  2. public class Person {
  3. private String name;
  4. private Address address;
  5. public String getName() {
  6. return name;
  7. }
  8. public void setName(String name) {
  9. this.name = name;
  10. }
  11. public Address getAddress() {
  12. return address;
  13. }
  14. public void setAddress(Address address) {
  15. this.address = address;
  16. }
  17. @Override
  18. public String toString() {
  19. return "Person [name=" + name + ", address=" + address + "]";
  20. }
  21. }
  1. package com.gp.spring.autowire;
  2. public class Address {
  3. private String city;
  4. private String street;
  5. public String getCity() {
  6. return city;
  7. }
  8. public void setCity(String city) {
  9. this.city = city;
  10. }
  11. public String getStreet() {
  12. return street;
  13. }
  14. public void setStreet(String street) {
  15. this.street = street;
  16. }
  17. @Override
  18. public String toString() {
  19. return "Address [city=" + city + ", street=" + street + "]";
  20. }
  21. }

再创建IOC配置文件

  1. <?xml version="1.0" encoding="UTF-8"?
  2. >
  3. <beans xmlns="http://www.springframework.org/schema/beans"
  4. xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:util="http://www.springframework.org/schema/util"
  5. xmlns:p="http://www.springframework.org/schema/p"
  6. xsi:schemaLocation="http://www.springframework.org/schema/beans
  7. http://www.springframework.org/schema/beans/spring-beans.xsd
  8. http://www.springframework.org/schema/util
  9. http://www.springframework.org/schema/util/spring-util-4.0.xsd">
  10. <bean id="address" class="com.gp.spring.autowire.Address"
  11. p:city="beijing" p:street="haidian"></bean>
  12. <bean id="person" class="com.gp.spring.autowire.Person"
  13. p:name="Alis" p:address-ref="address"></bean>
  14. </beans>

測试代码

  1. package com.gp.spring.autowire;
  2. import org.springframework.context.ApplicationContext;
  3. import org.springframework.context.support.ClassPathXmlApplicationContext;
  4. public class Main {
  5. public static void main(String[] args) {
  6. ApplicationContext ctx = new ClassPathXmlApplicationContext(
  7. "autowired.xml");
  8. Person p = (Person) ctx.getBean("person");
  9. System.out.println(p);
  10. }
  11. }

输出结果

Person [name=Alis, address=Address [city=beijing, street=haidian]]


以下我们来看一下是怎样进行自己主动装配的

改动配置文件

  1. <bean id="address" class="com.gp.spring.autowire.Address"
  2. p:city="beijing" p:street="haidian"></bean>
  3. <bean id="person" class="com.gp.spring.autowire.Person"
  4. p:name="Alis" autowire="byName"></bean>

添加代码autowire=”byName”,使用byName的方式进行自己主动匹配。

它就会依据person类中的setAddress属性匹配名为address的bean。

同理可知,byType匹配方式,匹配与setAddress类型一直的bean。


XML 配置里的 Bean 自己主动装配的缺点

  • 在 Bean 配置文件中设置 autowire 属性进行自己主动装配将会装配 Bean 的全部属性. 然而, 若仅仅希望装配个别属性时,

    autowire 属性就不够灵活了.
  • autowire 属性要么依据类型自己主动装配, 要么依据名称自己主动装配, 不能两者兼而有之.
  • 普通情况下,在实际的项目中非常少使用自己主动装配功能,由于和自己主动装配功能所带来的优点比起来。明白清晰的配置文档更有说服力一些

Bean的继承关系

  • Spring 同意继承 bean 的配置, 被继承的 bean 称为父 bean. 继承这个父 Bean 的 Bean 称为子 Bean
  • 子 Bean 从父 Bean 中继承配置, 包含 Bean 的属性配置
  • 子Bean也能够覆盖从父Bean中继承过来的属性
  • 父 Bean 能够作为配置模板, 也能够作为 Bean 实例. 若仅仅想把父 Bean 作为模板, 能够设置 bean的abstract 属性为 true, 这样 Spring 将不会实例化这个 Bean

来看下以下这段代码

  1. <bean id="address1" class="com.gp.spring.autowire.Address"
  2. p:city="鸡西" p:street="南岗"></bean>
  3. <bean id="address2" class="com.gp.spring.autowire.Address"
  4. p:city="鸡西" p:street="电台路"></bean>
  1. public static void main(String[] args) {
  2. ApplicationContext ctx = new ClassPathXmlApplicationContext(
  3. "context_relate.xml");
  4. Address address = (Address) ctx.getBean("address1");
  5. System.out.println(address);
  6. address = (Address) ctx.getBean("address2");
  7. System.out.println(address);
  8. }

输出结果

Address [city=鸡西, street=南岗]

Address [city=鸡西, street=电台路]

非常easy的属性注入,你是否注意到再配置文件中,注入的两条信息。大部分内容是同样的,比方同样的Bean,同样的值。

这里我们能够用一个Bean继承的做法。来简化配置。例如以下

  1. <bean id="address1" class="com.gp.spring.autowire.Address"
  2. p:city="鸡西" p:street="南岗"></bean>
  3. <bean id="address2" p:street="电台路" parent="address1"></bean>

这里用到了parent,继承自address1的Bean。然后我们在重写我们要改动的内容。


抽象Bean(abstract=”true”)

抽象的Bean是不同意被实例化的,我们看一个错误的代码

  1. <bean id="address1" class="com.gp.spring.autowire.Address"
  2. p:city="鸡西" p:street="南岗" abstract="true"></bean>
  3. <bean id="address2" p:street="电台路" parent="address1"></bean>

address1添加了abstract=”true”表示为抽象Bean

  1. public static void main(String[] args) {
  2. ApplicationContext ctx = new ClassPathXmlApplicationContext(
  3. "context_relate.xml");
  4. Address address = (Address) ctx.getBean("address1");
  5. System.out.println(address);
  6. address = (Address) ctx.getBean("address2");
  7. System.out.println(address);
  8. }

执行測试方法

我们会看到以下异常,意思为抽象类是不许被实现的。

Exception in thread “main” org.springframework.beans.factory.BeanIsAbstractException: Error creating bean with name ‘address1’: Bean definition is abstract

所以我们去掉address1的实现就可以。

  1. public static void main(String[] args) {
  2. ApplicationContext ctx = new ClassPathXmlApplicationContext(
  3. "context_relate.xml");
  4. // Address address = (Address) ctx.getBean("address1");
  5. // System.out.println(address);
  6. Address address = (Address) ctx.getBean("address2");
  7. System.out.println(address);
  8. }

通常抽象Bean使用方法,不指定详细的类,在其继承的子类中指定class。例如以下

  1. <bean id="address1" p:city="鸡西" p:street="南岗" abstract="true"></bean>
  2. <bean id="address2" class="com.gp.spring.autowire.Address"
  3. p:street="电台路" parent="address1"></bean>
  4. <bean id="address3" class="com.gp.spring.autowire.Address"
  5. p:street="和平大街" parent="address1"></bean>

依赖Bean的配置

当我们在注入Bean的信息的时候,假设要求某些信息必须录入,则这就是Bean的依赖。

比方我们注入一个person类信息,当中person有一个address的属性,前提要求address必需要被注入数据,这样这个人才有地址,也就是person依赖address

以下我们来看看代码

  1. <bean id="address" class="com.gp.spring.autowire.Address"
  2. p:street="和平大街" p:city="鸡西"></bean>
  3. <bean id="person" class="com.gp.spring.autowire.Person"
  4. p:name="pengpeng" depends-on="address"></bean>

输出内容

Person [name=pengpeng, address=null]

假设我们去掉address

  1. <!--
  2. <bean id="address" class="com.gp.spring.autowire.Address"
  3. p:street="和平大街" p:city="鸡西"></bean>
  4. -->
  5. <bean id="person" class="com.gp.spring.autowire.Person"
  6. p:name="pengpeng" depends-on="address"></bean>

会抛出一下异常

org.springframework.beans.factory.NoSuchBeanDefinitionException: No bean named ‘address’ is defined

假设前置依赖于多个 Bean,则能够通过逗号,空格或的方式配置 Bean 的名称


Bean的作用域

Bean的作用域能够理解为IOC容器中的Bean他的作用范围。我们通过以上的内容了解到获取到一个bean的信息通过以下方式

  1. Address address1 = (Address) ctx.getBean("address");

那比方如今我获取多个的时候会是什么样子的呢。我们做了下測试

  1. public static void main(String[] args) {
  2. ApplicationContext ctx = new ClassPathXmlApplicationContext(
  3. "context_relate.xml");
  4. Address address1 = (Address) ctx.getBean("address");
  5. Address address2 = (Address) ctx.getBean("address");
  6. System.out.println(address1 == address2);
  7. }

输出结果:true

可知IOC容器中的Bean都是单实例的。

我们能够通过scope来配置Bean的作用域。眼下有四种



当中主要用的singleton、prototype。

默认情况是singleton。

以下改动IOC配置

  1. <bean id="address" class="com.gp.spring.autowire.Address"
  2. p:street="电台路" p:city="鸡西" scope="prototype"></bean>

输出结果:false

另外两个request、session在web的应用开发中使用。兴许用到的时候单独介绍。


使用外部属性文件

我们在开发的时候会使用spring注入JDBC的连接池信息。代码例如以下

  1. <beans xmlns="http://www.springframework.org/schema/beans"
  2. xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
  3. xmlns:context="http://www.springframework.org/schema/context"
  4. xmlns:p="http://www.springframework.org/schema/p"
  5. xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd
  6. http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-4.1.xsd">
  7. <context:property-placeholder location="classpath:db.properties"/>
  8. <bean id="db" class="com.gp.spring.jdbc.DataSource">
  9. <property name="userName" value="${username}"></property>
  10. <property name="password" value="${password}"></property>
  11. </bean>
  12. </beans>

这里context:property-placeholder引入外部文件。然后通过${}方式获取信息。

db.properties代码例如以下

  1. username=root
  2. password=123456

Spring -- Bean自己主动装配&amp;Bean之间关系&amp;Bean的作用域的更多相关文章

  1. Spring中自己主动装配

    自己主动装配 在我们了解过constructor-arg和property装配中.都须要配置对应的属性和值或者引用,假设在比較复杂的项目中.就会使得XML的配置变得复杂,自己主动装配能够使用较少的配置 ...

  2. 002-Spring4 快速入门-项目搭建、基于注解的开发bean,Bean创建和装配、基于注解的开发bean,Bean初始化销毁、Bean装配,注解、Bean依赖注入

    一.项目搭建 1.项目创建 eclipse→project explorer→new→Project→Maven Project 默认配置即可创建项目 2.spring配置 <dependenc ...

  3. spring自己主动装配Bean属性

    spring提供了3种类型的自己主动装配 byName:把与Bean的属性具有同样名字(或者ID)的其它Bean自己主动装配到Bean的相应属性中. byType:把与Bean的属性具有同样类型的其它 ...

  4. spring 配置bean-自己主动装配

    版权声明:本文为博主原创文章,未经博主同意不得转载. https://blog.csdn.net/qilixiang012/article/details/28260477 概要:(蓝色为本节所讲) ...

  5. 什么是Spring的命名空间及使用Spring 的命名空间p 装配属性

    这个就要从XML说了,Spring的配置管理可以利用XML方式进行配置,而XML里面就有命名空间这个概念..实际上就和标签的意思有点像 你给一个命名空间以后,这个XML文件里面就可以用那个命名空间上下 ...

  6. Spring基础篇——bean的自动化装配

    上篇博文讲Spring的IOC容器时说道,虽然容器功能强大,但容器本身只是个空壳,需要我们主动放入装配对象,并告诉它对象之间的协作关系,然后容器才能按照我们的指示发挥它的魔力,完成装配bean的使命. ...

  7. Spring框架系列(二)--装配和注入Bean

    企业日常开发中,几乎都是Spring系的框架,无论是SSM.还是现在大火的SpringBoot+JPA/MyBatis,使用最大的目的就是简化开发 基本模块: 核心容器:Beans.Core.Cont ...

  8. Spring实战3:装配bean的进阶知识

    主要内容: Environments and profiles Conditional bean declaration 处理自动装配的歧义 bean的作用域 The Spring Expressio ...

  9. Spring实战2:装配bean—依赖注入的本质

    主要内容 Spring的配置方法概览 自动装配bean 基于Java配置文件装配bean 控制bean的创建和销毁 任何一个成功的应用都是由多个为了实现某个业务目标而相互协作的组件构成的,这些组件必须 ...

随机推荐

  1. django第10天(聚合查询,常用字段)

    django第10天 聚合查询 聚合函数的使用场景 单独使用:不分组,只查聚合结果 分组使用:按字段分组,可查分组字段与聚合结果 导入聚合函数 from django.db.models import ...

  2. 快速入门Sklearn

    主要确定sklearn的基本流程,然后把sklearn当做螺丝刀来用就行了,需要什么查什么. 基本流程 首先我们回顾一下机器学习的基本流程: 特征工程,包括了数据清洗,数据标准版化,特征选取,特征降维 ...

  3. mac securecrt自动保存密码

    一.问题描述 mac有自带的终端,可以运行ssl和sftp,但是目录操作,文件操作和文件上传是分开的,很不方便,并且文件上传命令需要文件的全路路径. 使用securecrt能方便的解决上述的问题,并且 ...

  4. iptables防火墙简介

    原文地址:http://drops.wooyun.org/tips/1424 一.iptables介绍 linux的包过滤功能,即linux防火墙,它由netfilter 和 iptables 两个组 ...

  5. Mac下Python和Pycharm之virtualenv

    一.python如何配置virtualenv   1.安装virtualenv pip3 install virtualenvpip install -i https://pypi.tuna.tsin ...

  6. Leetcode 388.文件的最长绝对路径

    文件的最长绝对路径 假设我们以下述方式将我们的文件系统抽象成一个字符串: 字符串 "dir\n\tsubdir1\n\tsubdir2\n\t\tfile.ext" 表示: dir ...

  7. 修改系统dpi

    系统dpi设置不合理,会导致屏幕显示效果差.配置系统dpi设置ro.sf.lcd_density的值即可,不同项目设置位置不同,以高通为例:需要修改 项目/device/qcom/common/roo ...

  8. DP的序--Codeforces956E. Wardrobe

    $n \leq 10000$个盒子,有高度,高度总和$\leq 10000$,盒子有重要的和不重要的,问最多有多少重要盒子的底端在区间$[L,R]$. 这是个入门级的DP,但需要一点胆量MD这题能放D ...

  9. oracle 连接数据库以及查看当前用户、当前数据库实例

    sql>show user;查看当前用户 sql>show parameter instance_name;查看当前数据库实例 例如: sqlplus登录:用sys用户登录(密码是1234 ...

  10. 解决U3D4.1.5或以上无法启动MONODEV的方法

    通常会报这样的错误 System.EntryPointNotFoundException: Unable to find an entry point named 'gtksharp_list_get ...