举例理解JDK动态代理
JDK动态代理
说到java自带的动态代理api,肯定离不开反射。JDK的Proxy类实现动态代理最核心的方法:
public static Object newProxyInstance(ClassLoader loader,
Class<?>[] interfaces,
InvocationHandler h)
这个方法的作用:在运行时,动态创建一组指定接口的实现类对象。其中的三大参数:
ClassLoader loader
- 类加载器,主要作用是用来加载类的,把.class文件加载到jvm的方法区中,形成class对象
Class<?>[] interfaces
- 实现的接口列表
InvocationHandler h
- InvocationHandler 是一个接口,里面有且只有一个方法invoke(Object proxy, Method method, Object[] args),后面会介绍。
我们可以先看个简单的例子:
public class DynamicProxyDemo {
@Test
public void test1() {
ClassLoader loader = this.getClass().getClassLoader();
Class[] classes = {Human.class, Car.class};
InvocationHandler h = new InvocationHandler() {
@Override
public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
System.out.println("来了,老弟~");
return null;
}
};
Human human = (Human) Proxy.newProxyInstance(loader, classes, h);
human.male();
human.toString();
human.getClass();
}
}
interface Human {
Object male();
}
interface Car {
Object bmw();
}
输出:
来了,老弟~
来了,老弟~
可以看到,代码并没有报错,因为Proxy.newProxyInstance(loader, classes, h)返回的对象是实现了指定接口的类对象,所以强转成Human没有问题,当调用Human对象的方法时,会执行InvocationHandler里的invoke方法的语句。但是我当我调用getClass()方法时,并没有执行对应的语句,这是由于此方法是native方法,是调用本地的方法。
既然调用代理对象的所有方法(个别除外)都会调用某个方法(invoke()),我们可以在里面进行任意操作,达到前置或者后置增强的效果。
以下这图可以解析invoke(Object proxy, Method method, Object[] args)方法里的参数和human接口带参数的方法之间的关系:

输出:
来了,老弟~
科比
此方法也包含三大参数:
- Object proxy
- 当前对象,即生成的代理对象
- Method method
- 当前被调用的方法,即目标方法
- Object[] args
- 方法传入的参数
未完待续。
举例理解JDK动态代理的更多相关文章
- 从Mybatis源码理解jdk动态代理默认调用invoke方法
一.背景最近在工作之余,把开mybatis的源码看了下,决定自己手写个简单版的.实现核心的功能即可.写完之后,执行了一下,正巧在mybatis对Mapper接口的动态代理这个核心代码这边发现一个问题. ...
- JDK动态代理深入理解分析并手写简易JDK动态代理(下)
原文同步发表至个人博客[夜月归途] 原文链接:http://www.guitu18.com/se/java/2019-01-05/27.html 作者:夜月归途 出处:http://www.guitu ...
- java jdk动态代理学习记录
转载自: https://www.jianshu.com/p/3616c70cb37b JDK自带的动态代理主要是指,实现了InvocationHandler接口的类,会继承一个invoke方法,通过 ...
- 模拟实现jdk动态代理
实现步骤 1.生成代理类的源代码 2.将源代码保存到磁盘 3.使用JavaCompiler编译源代码生成.class字节码文件 4.使用JavaCompiler编译源代码生成.class字节码文件 5 ...
- jdk动态代理举例
JDK动态代理是基于接口的代理,下面举例说明 代理类:proxy,代理动作必须要基于一个proxy实例来执行 代理执行类:实现InvocationHandler,案例中是TestInvocationH ...
- java jdk动态代理模式举例浅析
代理模式概述 代理模式是为了提供额外或不同的操作,而插入的用来替代”实际”对象的对象,这些操作涉及到与”实际”对象的通信,因此代理通常充当中间人角色. java中常用的动态代理模式为jdk动态代理和c ...
- JDK动态代理深入理解分析并手写简易JDK动态代理(上)
原文同步发表至个人博客[夜月归途] 原文链接:http://www.guitu18.com/se/java/2019-01-03/27.html 作者:夜月归途 出处:http://www.guitu ...
- jdk动态代理和cglib动态代理底层实现原理超详细解析(jdk动态代理篇)
代理模式是一种很常见的模式,本文主要分析jdk动态代理的过程 1.举例 public class ProxyFactory implements InvocationHandler { private ...
- 代理模式详解:静态代理、JDK动态代理与Cglib动态代理
代理模式简介分类 概念 代理,是为了在不修改目标对象的基础上,增强目标方法的业务逻辑. 客户类需要执行的是目标对象的目标方法,但是真正执行的是代理对象的代理方法,客户类对目标对象的访问是通过代 ...
随机推荐
- Android 跨进程数据共享
Android 开发过程中,基于功能隔离.进程安全.进程保活等等考虑,我们经常需要为应用划分进程,然后不得不面临跨进程通信和跨进程共享数据的挑战. 跨进程通信 相对来说,跨进程通信比较简单,常用的方式 ...
- afn3.0源码解析---AFURLRequestSerialization
AFHTTPRequestSerialization: @方法1 - (NSMutableURLRequest *)requestWithMethod:(NSString *)method URLSt ...
- windows red5相关
red5部署 前段时间把red5服务器搭建好了,现在记录下是如何搭建的.1,下载对应版本的red5https://github.com/Red5/red5-server/releases2,如果没有安 ...
- linux pwd命令 显示当前所在路径
pwd 显示当前所在路径 [root@MongoDB ~]# pwd /root
- kubernetes命令详情
查看客户端和服务器侧的版本信息 kubectl version 列出当前版本的kubernetes的服务器端所支持的api版本信息 kubectl api-versions 查看帮助,语法格式 kub ...
- js类型转换比较表格
JavaScript类型转换表格 值 转换为 字符串 数字 布尔值 对象 undefined "undefined" NaN false throw TypeEr ...
- btcpool之BlockMaker
一.简介 BlockServer将StratumServer发送的solvedshare数据(块头和coinbase交易)与GbtMaker发送的rawgbt数据(其他交易)一起组装成一个块,然后通过 ...
- jmeter-PC注册遇到的问题与解决
2019-04-26问题:
- [LeetCode] 45. Jump Game II_ Hard tag: Dynamic Programming
Given an array of non-negative integers, you are initially positioned at the first index of the arra ...
- virtual dom 简单了解
管理应用程序状态和用户界面的同步一直是前端UI开发复杂性的主要来源.目前出现了不同的方式来处理这个问题.本文简单讨论其中一种方式virtual dom. 文章概要: virtual dom 基本概念, ...