初识继承、 组合、动态代理

来源:互联网 发布:扫矿老僧软件使用视频 编辑:程序博客网 时间:2024/04/28 04:32

假如我们有一段代码,要在这段代码前加权限,日志,过滤等操作我们该怎么办?我的第一想法就是直接在代码前写代码就好了,可是这样会使业务逻辑的代码量增大,不能使我们专注于业务逻辑的思考,并且如果我们看不到原来的代码就更加无所适从了。

下面通过代码的方式提出三种方法方便大家处理以上情况

首先定义一个接口

public interface Car {public void running();}
其次是他的实现类

public class CarImpl implements Car{@Overridepublic void running() {//System.out.println("start");System.out.println("the beautiful girl in the car is crying");//System.out.println("end");}}
然后是测试类

public static void main(String[] args) {Car car = new CarImpl();car.running();}
}

假如我们需要在running前后加些代码,又拿不到CarImpl源码,我们可以采用以下几种方法来解决这个问题

一:继承

我们可以再写一个实现类CarImpl2继承CarImpl即可,代码如下

public class CarImpl2 extends CarImpl{@Overridepublic void running() {System.out.println("start");super.running();System.out.println("end");}}

测试类如下

public static void main(String[] args) {Car car = new CarImpl2();car.running();}
这样我们就实现了在前后加代码的功能了,可是这种方法并不好,耦合性太强,父类改了,子类也不得不会做出相应变化,不灵活。并且如果还有别的实现类要增加代码,还得再继承一遍,再写一次代码。

二 :组合

相较于继承,组合具有更大的灵活性,代码如下

这里CarImpl2实现Car接口

public class CarImpl2 implements Car{/* * 相当于 * private Car car = new CarImpl(); **/private Car car;public CarImpl2(Car car){this.car = car;}@Overridepublic void running() {System.out.println("start");car.running();System.out.println("end");}}

测试类如下:

public static void main(String[] args) {Car car = new CarImpl2(new CarImpl());car.running();}
这种写法在代理模式里属于静态代理,他只能为一个类服务,仍有不方便,如果我要是想在每一个类每一个方法前都要加上一段代码,或者说有的要加有的不加,这样我们就不是很方便,如果我们能把这些东西单独拿出来,写在一个xml文件里想必是极好的,这就是 spring的AOP机制,当然今天我们不聊AOP,而是聊AOP背后的原理,动态代理。代理模式分为动态代理和静态代理,代理类对象本身并不真正实现服务,而是通过调用委托类对象的相关方法来提供服务,具体含义大家可以去网上找一下,很多,我不详述。

三:动态代理

如果不深究,动态代理其实就只要记住一个接口一个类即可,即InvovationHandler,Proxy;

这里我们写一个CarProxy类,他继承了InvovationHandler接口,如下;

public class CarProxy implements InvocationHandler {private Object target;public CarProxy(Object target){this.target = target;}@Overridepublic Object invoke(Object proxy, Method method, Object[] args)throws Throwable {System.out.println("start");method.invoke(target, args);System.out.println("end");return null;}}

测试类如下:

public static void main(String[] args) {Car car = new CarImpl();CarProxy carProxy = new CarProxy(car);Car car1 = (Car)Proxy.newProxyInstance(car.getClass().getClassLoader(), car.getClass().getInterfaces(), carProxy);car1.running();}



以下两篇大神的文章阐释了Jdk动态代理,贴出来供大家参开

http://www.cnblogs.com/jqyp/archive/2010/08/20/1805041.html

http://www.cnblogs.com/xiaoluo501395377/p/3383130.html

0 0
原创粉丝点击