概念
Spring是分层的JavaSE/EE应用full-stack 轻量级 开源的 半成品框架,以 IOC(Inverse Of Control:反转控制)和 AOP(Aspect Oriented Programming:面向切面编程)为内核。
Spring优势
方便解耦,简化开发
方便集成各种优秀框架
方便程序的测试
切面编程的支持
声明式事务的支持@Transactional
降低JavaEE API的使用难度
IOC
IOC 反转控制
控制反转是将对象的控制权给了spring框架 并将这些对象放在一个bean容器里
bean的生命周期
当scope的取值为singleton时(系统默认的)
Bean的实例化个数:1个 Bean的实例化时机:
对象创建:当Spring核心文件被加载时,创建容器时,对象就被创建了
对象运行:只要容器在,对象一直活着
对象销毁:当应用卸载,销毁容器时,对象就被销毁了
当scope的取值为prototype时
Bean的实例化个数:多个 Bean的实例化时机:
对象创建:当调用getBean()方法,对象实就被创建出来了
对象运行:只要对象在使用中,就一直活着
对象销毁:当对象长时间不用时,被 Java 的垃圾回收器回收了 ( jvm gc垃圾回收)
Aop
什么是 AOP
-
AOP 是 OOP 的延续,
-
AOP可以对业务逻辑的各个部分进行隔离,从而使得业务逻辑各部分之间的耦合度降低,提高程序的可重用性,同时提高了开发的效率。
AOP 的作用及其优势
-
作用:在程序运行期间,在不修改源码的情况下对方法进行功能增强
-
优势:减少重复代码,提高开发效率,并且便于维护
AOP 的底层实现
-
AOP 的底层是通过 Spring 提供的的动态代理技术实现的。在运行期间,Spring通过动态代理技术动态的生成代理对象,代理对象方法执行时进行增强功能的介入,在去调用目标对象的方法,从而完成功能的增强。
常用的动态代理技术
-
JDK 代理 : 基于接口的动态代理技术
-
cglib 代理:基于父类的动态代理技术
JDK 代理
/**
* 接口类
*/
public interface TargetInterface {void say();
}/**
* 目标类
*/
public class Target implements TargetInterface {
public void say() {
System.out.println("目标类执行了");
}
}
public static void main( String[] args ) {
final Target target = new Target();
//生成了一个代理类对象proxy
TargetInterface proxy = (TargetInterface)Proxy.newProxyInstance(
//第一个参数被代理类的类加载器
target.getClass().getClassLoader(),
//第二个参数target的所以实现接口
target.getClass().getInterfaces(),
//第三参数是InvocationHandler
new InvocationHandler() {
public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
System.out.println("前面增强");
Object invoke = method.invoke(target, args);
System.out.println("后置增强");
return invoke;
}
});
proxy.say();
}public interface ClacInterface {
int add(int a ,int b );
}public class MyClac implements ClacInterface{
@Override
public int add(int a, int b) {
System.out.println("a+b"+"="+(a+b));
return a+b;
}
}public static void main(String[] args) {
//创建接口的实现类对象,也就是被代理对象
ClacInterface myClac = new MyClac();
//获取被代理实现类对象的Class对象
Class<? extends ClacInterface> clazz = myClac.getClass();
//第一个参数,被代理对象的类加载器
ClassLoader classLoader = clazz.getClassLoader();
//第二个参数,被代理对象实现的所有接口数组
Class<?>[] interfaces = clazz.getInterfaces();
//通过调用Proxy.newProxyInstance的方法来创建一个代理类对象来代理myClac对象
ClacInterface proxyBean = (ClacInterface)Proxy.newProxyInstance(classLoader, interfaces, new InvocationHandler() {
//第三个参数InvocationHandler的实现类,这里用了匿名内部类的方式
@Override
//重写InvocationHandler的invoke方法,他有三个参数可以供我们使用
public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
//第一个参数proxy 可以通过proxy.getClass().getClassName() 来查看对象,是一个匿名的Proxy的代理类
System.out.println("proxy.getClass().getName() = " + proxy.getClass().getName());
System.out.println("前置增强------");
//第二个参数method 也就是被代理对象myClac对象的方法,可以通过method调用myClac的方法
//第三个参数args 也就是MyClac方法执行时传入的实际参数
//method.invoke的返回值就是myClac方法的返回值
Object invoke = method.invoke(myClac, args);
System.out.println("后置增强------");
return invoke;
}
});
System.out.println("proxyBean.add(1, 3) = " + proxyBean.add(1, 3));
}
Aop相关概念
# Target(目标对象):代理的目标对象 也就是你要那个功能进行增强和修改 那么这个功能就是目标对象
# Proxy (代理):把目标对象进行增强产生了一个代理结果
# Joinpoint(连接点):所谓连接点是指那些被拦截到的点。在spring中,这些点指的是方法,因为spring只支持方法类型的连接点。 可以安装8倍境的地方 (就是把目标对象和代理结果可以连接的点 有多个)
# Pointcut(切入点):所谓切入点是指我们要对哪些 Joinpoint 进行拦截的定义。 (就是把目标对象和代理结果连接起来的点 只有一个)
# Advice(通知/ 增强):(插入的功能)
# Aspect(切面):是切入点和通知的结合
# Weaving(织入):是指把增强应用到目标对象来创建新的代理对象的过程。spring采用动态代理织入,而AspectJ采用编译期织入和类装载期织入。 (安装的过程)