java架构解密——双容器优化aop

上篇博客中,提出,优化是个无止境的过程,的确,随着需求的变化,软硬件基础的升级,我们越来越不考虑代码的容量,而是考虑代码的质量,但是随着研究的深入,到了某个阶段,我们也要考虑代码的容量问题,这时,容器的概念,脱颖而出,在上篇博客将服务类作为一个接口传入,实际在后台是一个map容器,我们不仅包含了map的全部实现,还实现了服务类的叠加,但是美中不足的是,我们的业务类,还是单个的对象,就如下图:

类图改造

这时,我们如果想为更多的业务提供服务,就必须编写更多的aop,这不符合我们的原则,基于这一点,我做了以下的调整,大家先看类图:

1.1,回顾上个版本类图:

1.2,改造后的类图:

代码实现:

我们将业务类做成了容器,然后代理类持有这个容器,这个容器的所有子元素,通过遍历,就都拥有了服务类的所有方法:

2.1,业务容器:

<pre name="code" class="java"><span style="font-size:18px;">/**
 * 业务类容器:
 * 	用map盛放要切入服务的业务类
 *
 * @author 许恕
 * @version 3.0.0 , 2015年6月16日 下午4:41:28
 */
public class DoMehds  implements IDoMehds {
	//盛放执行业务的map
	private  HashMap<String,Object> DoBeans;

	//获取业务map
	public HashMap<String, Object> getDoBeans() {
		return DoBeans;
	}

	//设置业务map
	public void setDoBeans(HashMap<String, Object> doBeans) {
		DoBeans = doBeans;
	}

}
</span>

2.2,代理类变化:

<span style="font-size:18px;"></span><pre name="code" class="java"><span style="font-size:18px;">/**
 * 打招呼动态代理类,给业务类添加功能
 * 前一版本为JDK代理实现
 * 	本次添加执行方法之前打印到控制台‘befor’
 * 	本次添加执行方法之后打印到控制台‘after’
 *本次版本为DGLIB代理
 *	换代理类原因,JDK代理要求被代理类必须实现某接口,因为它底层实现是新建一个类,实现和被代理类相同的接口
 *	用代理类新建的业务类代替原业务类
 *	CGLIB代理是新建一个类,继承自被代理类,用新建的代理类替换掉原业务类,就不需要接口了
 *
 *5.0版本增加服务组装容器,将服务从代理类中抽离出去了,我们的代理类成为了一个bean
 *6.0将服务容器定义为接口
 *7.0增加业务容器
 * @author 许恕
 * @version 3.0.0 , 2015年6月16日 下午3:20:13
 */
public class CGLibDynamicProxy implements MethodInterceptor {  

	//服务类容器
	private IProxyMehds proxyMehds;
	//业务类容器
    private DoMehds doMehds;
  //代理工厂类:单例模式,优化内存开销
    private static CGLibDynamicProxy instance = new CGLibDynamicProxy();  

    //构造函数
    private CGLibDynamicProxy() {
    }  

    //获取cglib代理工厂类
    public static CGLibDynamicProxy getInstance() {
        return instance;
    }  

    /**
     * 使用代理工厂生成某个类的代理
     *
     * @param cls 要代理的类
     * @return 返回已经代理好的类
     */
    @SuppressWarnings("unchecked")
    public <T> T getProxy(Class<T> cls) {
        return (T) Enhancer.create(cls, this);
    }  

    //获取业务容器
    private void getProxyToDoMap(){

    	//从业务容器中获取业务map
    	HashMap<String,Object> mapDo = doMehds.getDoBeans();

    	//循环给业务map中的业务类增加代理
    	for (HashMap.Entry<String, Object> entry : mapDo.entrySet()) {

    		//获取map中的对象
    	    String objectKey = entry.getKey();
    	    Object objectValure = entry.getValue();

    	    //重新更新map中的对象:代替原业务方法
    	    mapDo.put(objectKey, getProxy(objectValure.getClass()));
    	}

    }

    //重写被代理对象的方法执行
    //所有的方法执行,到反射的级别都是invoke,重写了这个方法,就重写了所有的方法执行,实现了代理
    @Override
    public Object intercept(Object target, Method method, Object[] args, MethodProxy proxy) throws Throwable {
    	//重要改进:从服务容器中执行方法,不再是写死的!
    	proxyMehds.beforeBean(); 

    	//方法正常执行的语句
        Object result = proxy.invokeSuper(target, args);

        //重要改进:从服务容器中执行方法,不再是写死的!
        proxyMehds.afterBean(); 

        return result;
    }

    //服务容器的get方法
	public IProxyMehds getProxyMehds() {
		return proxyMehds;
	}

	//服务容器的set方法
	public void setProxyMehds(IProxyMehds proxyMehds) {
		this.proxyMehds = proxyMehds;
	}

	//业务容器get方法
	public DoMehds getDoMehds() {
		return doMehds;
	}

	//业务容器set方法
	public void setDoMehds(DoMehds doMehds) {
		this.doMehds = doMehds;
		getProxyToDoMap();
	}  

}</span>

总结:

任何事物,都是有个诞生发展的过程,人类至今发明的东西,都是来自于人类自己的生活,在学习的过程中,想象生活,我们有时候,就会豁然开朗,举个例子:

小明要有个快递要给小李邮过去,小明找到邮递员,签字完成,过了3天小李收到了,邮递的过程就好像咱们的aop一般,对用户来说是透明的,拆箱和装箱的过程,交给各自自己负责就好,这不就是面向对象吗!

当然,优化如此就完美了吗?当然没有,下篇博客,咱们继续对aop做深入的了解和优化!

时间: 2024-08-27 11:28:48

java架构解密——双容器优化aop的相关文章

java架构解密——用接口改造AOP

优化是个无止境的工作,在AOP的路上,我们走得很远,但是还有很多的工作,我们没有做,比如,将aop的业务部分封装成容器,将aop的服务部分改造成面向接口的,这样就不受具体的形式上的限制了!这样AOP的优化,就又前进了一步,也是符合咱们的面向接口编程的思想,下面就和我一起研究下如何将接口的思想融入到aop的实现中. 回顾: 在上篇博客中,我们将aop的服务封装到了容器中: 这样的好处就是我们可以使用配置文件扩展服务类,服务类不再受限于具体的形式与方法,而我们封装的服务类和动态代理,构成了这样的一个

java架构解密——Spring框架的AOP

一直以来,我们应用了不少的AOP框架,但是对于AOP的底层实现却没有过多的深入,古话就是"知其然,不知其所以然",随着AOP学术讨论的骤然兴起,我也开拓了自己的眼界,深入了解了AOP这个五彩斑斓的世界! 先来看看大众的定义: 百度百科: 在软件业,AOP为Aspect Oriented Programming的缩写,意为:面向切面编程,通过预编译方式和运行期动态代理实现程序功能的统一维护的一种技术.AOP是OOP的延续,是软件开发中的一个热点,也是Spring框架中的一个重要内容,是函

java架构解密——AOP之动态代理实现

在上篇博客中,我们在宏观上介绍了AOP的底层实现,具体见博客java架构解密--Spring框架的AOP,在博客中,我们讲述了Aop的一些设计上的思路,今天,咱们就具体的实现,和大家一起探讨,看看AOP是怎么一步一步走到今天,而且有些图,也要做些纠正! 一,代码演变 前提:最初要实现的功能(打招呼) 代码: 接口: <span style="font-size:18px;">public interface Greeting { void sayHello(String n

java架构解密——深入再造AOP

在上篇博客中,大家和我一起研究了AOP的基本实现,但是,也给大家遗留了很多问题,在这篇博客,咱们一起研究如何针对这些问题进行持续的优化,看看在咱们的手里,AOP会成长为一个什么样的东西! 回顾: 看看上篇博客中,咱们一起实现的AOP类图: 咱们看看在CGLIB类里的问题 <span style="font-size:18px;">public class CGLibDynamicProxy implements MethodInterceptor { private sta

java架构解密——实时动态aop

在上篇博客中个,咱们一起组建了一个容器,里面封装了业务,这样,咱们就将业务和服务的组装放到了客户端,而客户端就相当于咱们的开发中使用到的配置文件,大家发现问题了吗?就是我不能动态改动了?业务容器在代理完成后,重新添加一个容器,这时候,是不被允许的,那这个容器就是个编译时起作用的容器,他就丧失了很多的灵活性! 那怎么办呢?实际就是调换一下调用顺序就好,大家看看结果: 1,类图对比 改造后类图 2,代码实现: 2.1代理类的变化: /** * 打招呼动态代理类,给业务类添加功能 * 前一版本为JDK

java架构解密——Spring框架的ioc自我实现

在java的开发中,经常使用的框架当属SSH,而在这张框架中,我们首先接触到的就是神奇的Spring,虽然有N多前辈说Spring就是N多公共代码的集合,是帮助我们实现了,我们很久之前就想实现或者已经实现的好的点子的集合,但是作为一名合格工程师,怎么能不懂spring的底层实现呢!在今天咱们就一起探索Spring是怎么完成IOC工作的,也自己做一个简单Spring框架! 1,Spring中Bean的定义 作用:在spring中使用的bean,都有某些公共属性,此类就是对公共属性的定义 <span

2018年java架构师分布式性能优化 附带源码

下载地址:百度网盘下载 教程内容: 第1章STL实用入门教程 第2章C++编码规范 第3章GDIGDI+从入门到精通 第4章COM实用入门教程 第5章Windows窗口高级编程 第6章Boost深入剖析之使用技巧 第7章VC++实战调试技巧 第8章静态库与动态库编程 第9章面向对象实践编程 第10章文件打包技术详解 第11章多线程编程技术详解 第12章XML永久化与解析编程详解 第13章C++高级编程 第14章SVN版本管理 第15章Windows核心编程 第16章C++设计模式教程 原文地址:

JAVA开发之大型互联网企业高并发架构Tomcat服务器性能优化视频教程

课程目标熟练掌握高并发架构Tomcat服务器性能优化. 适用人群对计算机,java开发人员,Java架构师,运维感兴趣的朋友! 课程简介Tomcat是Apache软件基金会(Apache Software Foundation)的Jakarta 项目中的一个核心项目,由Apache.Sun和其他一些公司及个人共同开发而成.Tomcat服务器是一个免费的开放源代码的Web应用服务器,属于轻量级应用服务器,在中小型系统和并发访问用户不是很多的场合下被普遍使用,是开发和调试JSP程序的首选. Tomc

java架构师、高性能、高并发、高可用、高可扩展、性能优化、集群、电商网站架构

15套java架构师.集群.高可用.高可扩展.高性能.高并发.性能优化.Spring boot.Redis.ActiveMQ.Nginx.Mycat.Netty.Jvm大型分布式项目实战视频教程 视频课程内容包含: 高级Java架构师包含:Spring boot.Spring  cloud.Dubbo.Redis.ActiveMQ.Nginx.Mycat.Spring.MongoDB.ZeroMQ.Git.Nosql.Jvm.Mecached.Netty.Nio.Mina.性能调优.高并发.to