首页 > 其他分享 >JDK动态代理

JDK动态代理

时间:2023-02-15 15:22:23浏览次数:43  
标签:JDK invoke Object 代理 接口 动态 方法 public

JDK动态代理是面向接口的。这是很多框架的基础。

JDK动态代理的原理是接口的实现, 所以接口一定要存在, 而且只能代理接口存在的方法.

首先动态代理类要实现InvocationHandler接口,该接口只有一个方法。

public Object invoke(Object proxy, Method method, Object[] args)
// proxy 参数是代理对象本身,在整个动态代理实现的过程中没有用到。
// method是代理对象调用的方法,args是方法的参数

需求:现在有一个房东host要出租房子,但是自己又非常懒,不想自己带人看房,议价之类,所以想让中介帮其租房子,此时中介就是个代理。

由于JDK动态代理是面向接口的,所以先有一个Rent接口代表出租的动作。

package com.ldt.pojo;

public interface Rent {
    void rent();
}

再有一个房东。

package com.ldt.pojo;

public class Host implements Rent{
    @Override
    public void rent() {
        System.out.println("房东要把房子租出去");
    }
}

再有一个动态代理类。

package com.ldt.pojo;

import java.lang.reflect.InvocationHandler;
import java.lang.reflect.Method;
import java.lang.reflect.Proxy;

public class ProxyInvocationHandler implements InvocationHandler {

    // 被代理的接口
    private Object target;

    public void setTarget(Object target) {
        this.target = target;
    }

    // 动态生成代理类
    public Object getProxy() {
        return Proxy.newProxyInstance(this.getClass().getClassLoader(), target.getClass().getInterfaces(), this);
    }

    // 处理代理实例,并返回结果
    @Override
    public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
        seeHouse();
        Object result = method.invoke(target, args);
        hetong();
        return result;
    }

    private void seeHouse() {
        System.out.println("中介带看房子");
    }

    private void hetong() {
        System.out.println("签合同");
    }
}

需要注意的是Proxy.newProxyInstance方法,该方法是动态生成代理对象的,第一个参数是classloader,第二个参数是要代理的类的接口,此处是Rent接口,第三个参数是handler对象本身。可以看出handler类并不是代理类,只是生成代理需要的一个元素,我们实现的invoke方法也不是代理类的方法,而是代理类要调用的方法,就是说代理类中会调用handler.invoke方法。

开始测试:

这里有一个client要来租房子。

package com.ldt.pojo;

public class Client {
    public static void main(String[] args) {
        Host host = new Host();
        ProxyInvocationHandler proxyInvocationHandler = new ProxyInvocationHandler();
        proxyInvocationHandler.setTarget(host);
        // 生成代理类
        Rent proxy = (Rent) proxyInvocationHandler.getProxy();
        // 调用代理类的rent方法,就是这个方法中调用了handler的invoke方法
        proxy.rent();
    }
}

由于代理对象是动态生成的,如何通过调用rent方法进而调用invoke不是一个显示的过程,但是查看源码可以知道,Proxy.newProxyInstance方法在生成代理对象时,动态的实现了rent方法,并且在rent方法中调用了handler的invoke方法。

标签:JDK,invoke,Object,代理,接口,动态,方法,public
From: https://www.cnblogs.com/yuandaguangming/p/17123185.html

相关文章

  • CGLIB动态代理
    CGLIB动态代理是基于类继承的代理,不能被继承的方法也不能被代理,比如final,private修饰的方法.CGLIB中重要的两个概念:MethodInterceptor是方法拦截器,代理类只需......
  • uniapp中动态计算屏幕高度问题
    在html中可使用动态高度   在data中winHeight:'',在onLoad中this.scrollH() 在方法中使用//动态计算高度 scrollH:function(){ letsys=uni.getS......
  • win10无管理员权限下以压缩包方式安装JDK8
    使用场景:如果在没有管理员权限的情况下,无法运行.exe文件,可以使用这种方式安装,本次把JDK安装到D:\jdk-8u152一:获取JDK8的压缩包1.JDK8华为镜像地址  2......
  • 时隔多年,这次我终于把动态代理的源码翻了个地儿朝天
    本文内容整理自博学谷狂野架构师动态代理简介​ Proxy模式是常用的设计模式,其特征是代理类与委托类有同样的接口,代理类主要负责为委托类预处理消息、过滤消息、把消......
  • ps 如何制作动态打字图?
     1.情景展示有几句话,想以打字的形式出现,而不是干巴巴的几个字,如何实现这个有趣的效果呢?2.解决方案第一步:录制屏幕:将想展示的文字逐字打出来--》保存;第二步:将录......
  • JDK的安装
    JDK的安装安装JDK1.下载JDK(一般选择JDK8)2.选择安装路径,配置环境需要3.配置环境变量(1)我的电脑,属性,高级系统设置,环境变量(2)在系统变量里面新建环境变量,系统变量名......
  • 【Azure 应用服务】在App Service for Windows中实现反向代理
    问题描述如何在AppServiceforWindows(.NETStack)中,如何实现反向代理呢?正向代理:客户端想要访问一个服务器,但是它可能无法直接访问这台服务器,这时候这可找一台可以访......
  • Mybatis12 - 动态SQL
    动态SQLMybatis框架的动态SQL技术是一种根据特定条件动态拼装SQL语句的功能,它存在的意义是为了解决拼接SQL语句字符串时的痛点问题。Oneofthemostpowerfulfeatures......
  • 通过Vue解决跨域问题(proxy配置代理)【转载】
    当我们在用本机去找服务器要数据时会产生跨域问题,所以利用vue-cli去开启一个代理服务器。方法一:在vue.config.js中添加如下配置//开启代理服务器(方式一)devServer......
  • vue路由的使用,命名,参数,范式,嵌套,动态匹配
    基本使用:1,让Vue使用该VueRouter创建,Vue.use(VueRouter);2,创建router对象varrouter=newVueRouter({});3,在创建的router对象中配置路由对象,路由匹配的规则,var......