JAVA动态代理

代理的分类

代理分为静态和动态代理。
静态代理:硬编码实现的代理类,在程序被编译成.class文件时代理类就已经存在。
动态代理:代理类在运行时产生,运用jdk的反射机制动态创建而成。

静态代理

静态代理可以通过组合的方式来实现,下面看具体的demo实现:

public class ProxyTest {

    @Test
    public void proxyMethodTest() {
       
        StaticProxy staticProxy = new StaticProxy(new ClientObject());
        System.out.println(staticProxy.get());
    }
}

interface ClientObjectInterface {
    public String get ();
}

class ClientObject implements ClientObjectInterface {
    public String get () {
        return "hi";
    }
}

class StaticProxy implements ClientObjectInterface {
    ClientObject clientObject;

    public StaticProxy(ClientObject clientObject) {
        this.clientObject = clientObject;
    }

    public String get() {
        return "proxy " + clientObject.get();
    }
}

运行结果:
proxy hi

当我们在使用的过程中发现ClientObject这个类随着业务需求的变化已经变得不够用了,这是我们该怎么办?保持着对修改关闭,扩展开放的原则,我们可以通过上面那种静态代理的方式来实现业务需求的变化,当然下面还有一种比较灵活的动态代理的方式来处理上面这种case。

动态代理

动态代理又可以分为jdk库提供的和cglib库提供,这里我们主要讲讲jdk提供的动态代理。jdk代理对象是通过java.lang.reflect.Proxy#newProxyInstance来进行创建的。

public static Object newProxyInstance(ClassLoader loader,
                                          Class<?>[] interfaces,
                                          InvocationHandler h)

loader:被代理对象的classloader。
interfaces:被代理对象实现的接口。
h:invocation handler,用于分派执行代理方法。

下面看下具体的代理实现demo:

public class ProxyTest {

    @Test
    public void proxyMethodTest() {
        ClientObject clientObject = new ClientObject();
        ClientObjectInterface object = (ClientObjectInterface) Proxy.newProxyInstance(
            clientObject.getClass().getClassLoader(), clientObject.getClass().getInterfaces(),
            new ObjectProxy());
        System.out.println(object.get());
    }

}

interface ClientObjectInterface {
    public String get ();
}

class ClientObject implements ClientObjectInterface {
    public String get () {
        return "hi";
    }
}


class ObjectProxy implements InvocationHandler {

    public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
        System.out.println("methodName: " + method.getName());
        return "no hi";
    }
}

运行结果:
methodName: get
no hi

当然可以在代理对象里面做很多事情,本demo只是简单的替换了被代理对象的函数体。

使用场景

代理的使用场景主要集中在,某一业务需要委托代理类集中处理某一业务然后再执行具体的实现类的业务逻辑。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值