学习IOC(控制反转),学习Spring容器的重点之一
在学习Spring IOC的情况下,我们得先需要了解Spring容器提供的两种类型的IOC容器实现:
- BeanFactory:IOC容器的基本实现
- ApplicationContext:提供了更多的高级特性
Spring容器的几个重要模块:
Spring core:是核心库类,提供IOC服务。
Spring Contex:一般我们用于配置文件
AOP:提供AOP(面向切面编程的一种框架)服务
Spring Transactions:提供Spring事务管理操作
Spring JdbcTemplate:在Spring容器中进行(JDBC)数据库开发
AOP Aspects:Aspects框架是基于AOP(面向切面编程)的基础上进行自动生成动态代理的一种框架
轻量级Spring容器的优点在哪?
1.高内聚,低耦合
- Spring容器将对象之间的依赖关系交给了Spring来处理,减少了各个类之间的联系
2.提高了很多代码的复用性
- AOP面向切面编程,将统用的任务或者代码提取出来,提高了代码的复用性
1.Spring
1.1加入JAR包 4核心+1依赖
4核心(beans,core,Context,Expression)
1依赖(logging)
1.2 IOC(控制反转)案例
以前我们学习JAVA创建对象都是通过new一个对象来产生,而学习SPring容器后,我们可以通过xml配置文件来创建一个对象,也就是通过IOC来创建一个对象,我们最终的目的是面向接口编程,这样我们可以直接通过接口去创建接口的实现类的实例对象。而不是直接new产生,实现了低耦合。
也可以通过注解的方式来进行实例化对象:@Controller(“实例对象的id”):一般用于WEB层
@Service(“实例对象的id”):一般用于Sercvice层
@Repository(“实例对象的id”):一般用于Dao层
@Component:任何情况下都可以使用
IOC:xml配置文件如下:
IOC:测试类如下:
1.3DI(依赖注入)案例
在Spring容器中依赖IOC容器来动态注入对象或者一些值等外部资源时使用,即IOC容器的实例对象中组件了一些预定好的方式(入setter方法)来接收来自容器的资源注入。简单来说,就是往实例对象中注入一些资源,入对象,值等等(前提是在IOC的基础上进行)
DI:xml配置文件如下:
1.4Spring静态工厂
通过Spirng去创建一个静态工厂,实例化一个静态工厂对象,然后通过factory-method属性来生成另一个实例对象,而不需要再去创建另一个对象bean实例,前提是静态工厂中的方法是静态的static
静态工厂xml配置:
静态工厂类:
1.5实例化工厂
实例化工厂是通过创建一个实例化工厂对象,然后通过这个对象再创建另一个对象,其这个实例化工厂对象中的方法都是非静态的
实例化工厂的xml配置文件:
实例化工厂类:
1.6 Bean的种类
普通Bena :用于创建某个类的实例对象
FactoryBean:是一个特殊的Bean,具有工厂生成对象能力,只能生产特殊的Bean
例如:TransactionProxyFactoryBean(事务代理工厂Bean),ProxyFactoryBean(代理工厂Bean)
TransactionProxyFactoryBean:生产事务代理的
ProxyFactoryBean:生产动态代理的
1.7作用域
再spring容器中,可以在元素scope属性设置bean的作用域,以确定这个bean是单例还是多例的
单例:**singleton:**一个bean以单例的形式存在,是默认的
多例:**prototype:**每执行一次getBean就产生一个新的实例
xml配置文件中设置多例:
这时候,每执行一次getbean,产生的实例对象就不同:
1.8 生命周期
1.8.1 初始化和销毁
在目标类被执行前后,将执行初始化和销毁方法
<bean id="" class="" init-method=“自定义的初始化方法” destroy-method=“自定义的销毁方法”
指定目标类执行前后的方法:
1.在xml配置中配置:
2.自定义一个类,类中创建2个自定义的目标类执行前后的方法:
注意事项:必须是单例的,销毁方法执行需要通过close方法来执行。而close方法需要通过ApplicationContext接口的实现类ClassPathXmlApplicationContext来获取
1.8.2 BeanPostProcessor后处理Bean
Spring提供一种机制,只要实现了此接口BeanPostProcessor这个接口,并把实现这个接口的实现类提供给Spring容器,Spring容器会自动调用这个实现类中的实现方法
postProcessBeforeInitialization:初始化方法前执行
postProcessAfterInitialization:初始化方法后执行
而这个实现类的真正作用在于:Spring容器在获得这个实现类后,会生成一个工厂勾子,这个勾子的作用可以通过目标类来生成代理对象,这个接口的实现类也是AOP原理的底层
模拟:
A a =new A();<–目标类
这时候出现了一个BeanPostProcessor后处理Bean对象实例,并把a的实例对象传给了后处理Bean实例
a=B.before();<–初始化方法前执行
a.init();<–初始化方法
a=B.after(a);<–初始化方法后执行 在后处理Bean中传入了一个目标类实例对象,在这个后处理Bean的after方法中,把a对象生成了一个代理对象,并返回了一个处理后的a对象(代理),下面的a对象都会是代理对象执行方法
a.Useradd();<–目标方法 (这时候我们希望在目标方法执行生成一个代理对象,在目标方法前后执行(例如:开启事务,关闭事务))
a.Destory()<–销毁方法
在初始化方法后执行的postProcessAfterInitialization方法中生成一个代理
,并在目标方法前后创建开启事务和关闭事务
实现类写完后,然后把这个接口实现类装载到Spring容器中
在目标方法执行前后开启事务和结束事务。
从而产生出了2个问题,
问题1.如果有很多的目标类,那么后处理Bean后作用于某1个呢?还是所有的目标类?
答:所有的目标类
问题2.如果让后处理Bean处理某一个目标类呢?
通过一个参数beanname来获取bean的实例名称来处理某一个目标类