java动态代理机制详解

Spring的核心AOP的原理就是java的动态代理机制。

在java的动态代理机制中,有两个重要的类或接口:

1.InvocationHandler(Interface):

  每一个动态代理类都必须要实现InvocatonHandler这个接口,并且每个代理类的实例都关联到一个handler,当我们通过代理对象调用一个方法的时候,这个方法的调用就会被转发为由

InvocatonHandler这个接口的invoke方法来进行调用。

public Object invoke(Object proxy,Method method,Object[] args )throws Throwable
{
}

proxy:代表我们所代理的那个真实对象;

method:只带我们所要调用真实对象的某个方法的Method对象;

args:指代的是调用真实对象某个方法时接受的参数。

2.Proxy(Class)

  这个类的作用就是用来动态的创建一个代理对象的类,它提供了许多方法,但是我们用的最多的就是newProxyInstance这个方法:

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

loader:一个ClassLoder对象,定义了由那个ClassLoader对象来对生成的代理对象进行加载;

interface:一个Interface对象的数组,表示的是我将要给我的需要代理的对象提供一组什么借口,如果我提供了一组借口给他,那么这个代理对象就宣称实现了该接口(多态),这样我就能调用这组接口中的方法了;

h:一个InvocationHandler对象,表示的是当我这个代理对象在调用方法的时候,会关联到哪一个InvocationHandler对象上。

  

【代码清单--1】抽象对象角色:

 package com.huawei.subject;
/**
* 抽象对象角色
* @author Administrator
*
*/
public interface Subject
{
void rent();
void hello();
}

【代码清单--2】真实对象角色

 package com.huawei.subject.Impl;

 import com.huawei.subject.Subject;
/**
* 真实对象角色
* @author Administrator
*
*/
public class RealSubject implements Subject
{ @Override
public void rent()
{
System.out.println("我想要出租my building");
} @Override
public void hello()
{
System.out.println("租客你好");
} }

【代码清单--3】代理类

 package com.huawei.proxy;

 import java.lang.reflect.InvocationHandler;
import java.lang.reflect.Method; /**
* 动态代理角色
* @author Administrator
*
*/
public class DynamicProxy implements InvocationHandler
{
//这个是我们要代理的真实对象
private Object subject;
//构造方法,给我们要代理的真实对象赋初值
public DynamicProxy(Object obj)
{
this.subject = obj;
} @Override
public Object invoke(Object object, Method method, Object[] args)
throws Throwable
{
//可以在代理真实对象之前进行一些自己的操作
System.out.println("Mrthod :"+method);
//当代理对象调用真实对象的方法时,其会自动的跳转到代理对象的handler对象的invoke方法来进行调用
method.invoke(subject, args); //可以在代理真实对象之后进行一些自己的操作 return null;
} }

【客户端】--测试类

 package com.huawei;

 import java.lang.reflect.InvocationHandler;
import java.lang.reflect.Proxy; import com.huawei.proxy.DynamicProxy;
import com.huawei.subject.Subject;
import com.huawei.subject.Impl.RealSubject; public class Main { public static void main(String[] args)
{
//我们要代理的真实对象
Subject realSubject = new RealSubject();
//我们要代理哪个真实对象,就将该对象传进去,最后是通过该真实对象来调用其方法的
InvocationHandler handler = new DynamicProxy(realSubject);
/**
* 通过Proxy的newInstance方法来创建我们的代理对象
* 第一个参数handler.getClass().getClassLoader(),我们这里使用这个
* handler这个类的ClassLoader对象来加载我们的代理对象;
* 第二个参数realSubject.getClass().getInterface(),我们这里为代理对象提供的接口
* 是真实对象所实现的接口,表示我要代理的是该真实对象,这样我就能调用这组接口中的方法了;
* 第三个参数handler,这里讲这个代理对象关联到上方的InvocationHandler这个对象上
*/ Subject subject = (Subject)Proxy.newProxyInstance(handler.getClass().getClassLoader(),
realSubject.getClass().getInterfaces(),
handler); System.out.println(subject.getClass().getName()); subject.rent();
subject.hello(); } }

【运行结果】

com.sun.proxy.$Proxy0
Mrthod :public abstract void com.huawei.subject.Subject.rent()
我想要出租my building
Mrthod :public abstract void com.huawei.subject.Subject.hello()
租客你好

  通过Proxy.newInstance创建的代理对象是在JVM运行时动态生成的一个对象,它并不是我们的InvocationHandler类型,也不是我们定义的那组接口的类型,而是在运行时动态生成的一个对象,

并且明明方式都是这样的形式,以$开头,proxy为重,最后一个数字表示对象的标号。

subject.rent();
subject.hello();

  这里是通过代理对象来调用实现的那种接口中的方法,这个时候程序就会跳转到由这个代理对象关联到的handler中的invoke方法去执行,而我们

的这个handler对象又接受一个RealSubject类型的参数,表示我要代理的就是这个真实对象,所以此时就会调用handler中invoke方法去执行。

  由结果可知,也证明了当我们通过代理对象来调用方法的时候,实际就是委托有其关联到的handler对象的invoke方法中来调用,并不是自己真实调用,而是通过代理的方法来调用的。

java动态代理模式的更多相关文章

  1. JAVA动态代理模式(从现实生活角度理解代码原理)

    所谓动态代理,即通过代理类:Proxy的代理,接口和实现类之间可以不直接发生联系,而可以在运行期(Runtime)实现动态关联. java动态代理主要是使用java.lang.reflect包中的两个 ...

  2. 关于java动态代理模式

    1. 动态代理 动态代理就是通过代理类是代理类与相关接口不直接发生联系,而在运行期(Runtime)实现动态关联. 动态代理主要用到java.lang.reflect包中的两个类,Invocation ...

  3. Java动态代理模式浅析

    Java代理设计模式 - 静态代理 Java中的动态代理 - 调用处理器 代理设计模式的UML图: 我将首先介绍Java中的各种代理实现方法 Java代理设计模式 - 静态代理 这个例子非常简单,只有 ...

  4. java 动态代理模式(jdk和cglib)

    package proxy.dynamicproxy; import java.lang.reflect.InvocationHandler; import java.lang.reflect.Met ...

  5. Java 动态代理模式浅析

    目录 Java代理设计模式 - 静态代理 静态代理的优点 静态代理的缺点 Java中的动态代理 - 调用处理器 主要笔记: 动态代理类的限制 代理设计模式的UML图: 我将首先介绍Java中的各种代理 ...

  6. JAVA代理模式与动态代理模式

    1.代理模式 所谓代理,就是一个人或者一个机构代表另一个人或者另一个机构采取行动.在一些情况下,一个客户不想或者不能够直接引用一个对象,而代理对象可以在客户端和目标对象之前起到中介的作用.代理模式给某 ...

  7. Java设计模式系列之动态代理模式(转载)

    代理设计模式 定义:为其他对象提供一种代理以控制对这个对象的访问. 动态代理使用 java动态代理机制以巧妙的方式实现了代理模式的设计理念. 代理模式示例代码 public interface Sub ...

  8. Java静态代理与动态代理模式的实现

    前言:    在现实生活中,考虑以下的场景:小王打算要去租房,他相中了一个房子,准备去找房东洽谈相关事宜.但是房东他很忙,平时上班没时间,总找不到时间去找他,他也没办法.后来,房东想了一个办法,他找到 ...

  9. java jdk动态代理模式举例浅析

    代理模式概述 代理模式是为了提供额外或不同的操作,而插入的用来替代”实际”对象的对象,这些操作涉及到与”实际”对象的通信,因此代理通常充当中间人角色. java中常用的动态代理模式为jdk动态代理和c ...

随机推荐

  1. pH 值与曝气对硝化细菌硝化作用的影响

    http://wenku.baidu.com/view/c2723434eefdc8d376ee325d.html 摘要: 目的 探讨硝化细菌最佳工作条件,为应用和生产提供依据. 方法 通过人工调节液 ...

  2. sql 2008 R2添加对MySql的远程服务器链接

    (1).我的sql 2008 R2所在的系统为Windows server 2008 *64 (2).MySQL所在的系统为Windows server 2003 *86 我想要实现的是在sql 20 ...

  3. Statement及PreparedStatement执行多个sql

        这两个对象的区别: 1.Statement它更适合执行不同sql的批处理,它没有提供预处理功能,性能比较低. 2.PreparedStatement它适合执行相同的批处理,它提供了预处理功能, ...

  4. 二模01day1解题报告

    T1.音量调节(changingsounds) 有n个物品的背包(有点不一样,每个物品必须取),给出初始价值,物品价值可正可负(就是两种选择嘛),求可能的最大价值,不可能(<0或>maxs ...

  5. 使用DotNetOpenAuth搭建OAuth2.0授权框架——Demo代码简单说明

    前段时间随意抽离了一部分代码作为OAuth2的示例代码,若干处会造成困扰,现说明如下: public class OAuthController : Controller { private stat ...

  6. 【EF学习笔记10】----------主从表级联操作

    主从表 级联新增 Console.WriteLine("=========主从表 级联新增=========="); using (var db = new Entities()) ...

  7. 解析利用wsdl.exe生成webservice代理类的详解

    利用wsdl.exe生成webservice代理类:根据提供的wsdl生成webservice代理类1.开始->程序->Visual Studio 2005 命令提示2.输入如下红色标记部 ...

  8. JavaScript 常用算法

    1.排序算法 (1)冒泡排序,冒泡排序其实就是通过比较相邻位置的元素大小,如果左边比右边大,就交换位置,继续比较,实际上就是每轮比较都得出一个最大值,然后通过多伦比较得出. function bubb ...

  9. 加密和ssl机制细节

    1.1 背景知识 对称加密:加密解密使用同一密钥,加解密速度快.随着人数增多,密钥数量急增n(n-1)/2 非对称加密:使用公私钥配对加解密,速度慢.公钥是从私钥中提取出来的,一般拿对方公钥加密来保证 ...

  10. 终极优化_详解Win7旗舰版系统中可以关闭的服务

    Win7旗舰版系统是一款功能强大的系统,不过对于很多用户很多功能却使用不上,而支持功能的很多服务也多少占用了系统资源,那么我们可以通过关闭一些不使用的服务来达到让win7系统运行速度加快的目的.下面小 ...