欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页

设计模式之JDK动态代理

程序员文章站 2022-05-02 23:37:24
...
一、什么是动态代理
动态代理指做一件事,不用全部都亲力亲为,划分一部分给更专业的人去办理。
二、动态代理的特点
1、有两个角色:被代理人和代理人
2、有一件事必须做,但又不完全由自己做。
3、代理人拥有被代理人的资料。
三、怎么实现
1、创建一个接口
package com.fsl.proxy;

public interface People {
	
	//买火车票
	public void buyTrainTicket();
	
	public String getId();
	
	public String getName();
	
}



2、创建被代理人
package com.fsl.proxy;

//被代理人,张三
public class ZhangSan implements People {
	private String id;
	
	private String name;
	
	public ZhangSan() {
		
	}

	public ZhangSan(String id, String name) {
		super();
		this.id = id;
		this.name = name;
	}

	//张三要买火车票回家过年
	@Override
	public void buyTrainTicket() {
		System.out.println("我要买到赣州的火车票!");
	}

	public String getId() {
		return id;
	}

	public void setId(String id) {
		this.id = id;
	}

	public String getName() {
		return name;
	}

	public void setName(String name) {
		this.name = name;
	}

}




3、创建代理人
package com.fsl.proxy;

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

//代理人,黄牛
public class HuangNiu implements InvocationHandler {
	People target;
	
	public Object getInstance(People target) {
		this.target = target;
		Class clazz = this.target.getClass();
		return Proxy.newProxyInstance(clazz.getClassLoader(), clazz.getInterfaces(), this);
	}

	/**
	 * 原理:
	 * 1、拿到被代理对象的引用,然后获取到它的接口
	 * 2、JDK代理重新生成一个类,同时实现代理对象的所实现的接口
	 * 3、重新动态生成一个class字节码
	 * 4、然后编译,生成一个代理类
	 */
	
	@Override
	public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
		System.out.println("你好," + this.target.getName() + " 先生/女士");
		System.out.println("我是黄牛,请问您是要买到哪里的票?");
		System.out.println("==================================");
		method.invoke(this.target, args);
		System.out.println("==================================");
		System.out.println("您的票买到了,请拿好!");
		return null;
	}

}





测试类
package com.fsl.proxy;

import java.lang.reflect.Proxy;

public class ProxyTest {

	public static void main(String[] args) {

		People people = (People)new HuangNiu().getInstance(new ZhangSan("123456", "张三"));
		people.buyTrainTicket();
	}

}