代理模式扩展(二):动态代理

代理模式扩展(二):动态代理

动态代理就是要再运行过程中决定代理类实现哪个接口,应用了Java的反射机制的Proxy类,如果还不熟悉这个类的读者,请跳转到我的另一篇博客先学习一下。点击这里跳转

为什么要使用动态代理?

动态代理,最大的用处就是用来实现AOP(面向切面编程),在不改变已有代码结构的情况下,增强或控制对象的行为。

举例:追踪一个对象的方法调用

这个例子很简单,很显然是要增强对象的行为,再多说一句,这里使用普通的代理模式也可以实现,但是没有使用动态代理简单(对于普通代理来说,调用每个方法之前都要输出方法的名字,这样会又很多重复操作)。

使用动态代理代理要追踪的对象,然后在方法调用之前输出方法名即可。

class ProxyHandler implements InvocationHandler{

    private Object realSubject;

    public ProxyHandler(Object realSubject) {
        this.realSubject = realSubject;
    }
    @Override
    public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
        //在调用前输出方法的名字
        System.out.println(method.getName());
        //间接的调用realSubject.doSomething();
        return method.invoke(realSubject, args);
    }
}

通用的一种写法

要想封装Proxy.newInstance这个方法,不可能去修改Proxy类,所以需要新建一个类用来封装这个方法。

class SubjectDynamicProxy{
    public static Subject newProxyInstance(Subject subject) {
        ClassLoader loader = subject.getClass().getClassLoader();
        Class[] interfaces = subject.getClass().getInterfaces();
        InvocationHandler h = new ProxyHandler(subject);

        return Proxy.newProxyInstance(loader, interfaces, h);
    }
}

interface Subject{
    void doSomethingA();
    void doSomethingB();
    void doSomethingC();
}

class RealSubject implements Subject{
    @Override
    public void doSomethingA() {
    }

    @Override
    public void doSomethingB() {
    }

    @Override
    public void doSomethingC() {
    }
}

class ProxyHandler implements InvocationHandler{

    private Object realSubject;

    public ProxyHandler(Object realSubject) {
        this.realSubject = realSubject;
    }
    @Override
    public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
        System.out.println(method.getName());
        return method.invoke(realSubject, args);
    }
}

public class Client {
    public static void main(String[] args) {
        Subject subject = new RealSubject();
        Subject proxy = SubjectDynamicProxy.newProxyInstance(subject);

        proxy.doSomethingA();
        proxy.doSomethingC();
        proxy.doSomethingB();
}
发布了213 篇原创文章 · 获赞 116 · 访问量 8万+

猜你喜欢

转载自blog.csdn.net/qq2071114140/article/details/103552678