1 代理

我们不直接的去调用一个方法,这样可以不用去改动原来的代码。我理解就是一个AOP概念。

2 静态代理

静态代理很容易理解:我们编写一个代理对象,实现被代理对象相同的接口。在代理对象内部转调被代理对象。

写一个例子:
1.接口和被代理类

// 被代理对象接口
public interface Person 
{
	void eat();
	void study();
}
// 被代理的类
public class Student implements Person
{
	private String name = \"三和小钢炮\";
	public void eat() 
	{
		System.out.println(this.name + \"eat\");
	}
	public void study() 
	{
		System.out.println(this.name + \"study java\");
	}
}

2.静态代理类
静态代理类也实现Person接口,同时将代理对象传入其内部。

public class PersonProxy implements Person 
{
	private Person personed;
	public PersonProxy(Person person)
	{
		personed = person;
	}
	public void eat() 
	{
		System.out.println(\"eat before\");
		personed.eat();
	}
	public void study() 
	{
		System.out.println(\"study before\");
		personed.study();
	}
}

3.测试类
我们试下:

public class Test 
{
	public static void main(String[] args) 
	{
		Person person = new Student();
		Person proxy = new PersonProxy(person);
		proxy.study();
		proxy.eat();
	}
}

打印结果:
study before
三和小钢炮study java
eat before
三和小钢炮eat

3 动态代理

静态代理,必须一个个方法去适配,这样子不仅辛苦,也没有必要。我们用反射动态解决。

复用上面代码,我们写一个动态代理类:

public class PersonProxyHandler implements InvocationHandler
{
	private   proxyed;
	
	public PersonProxyHandler(  proxyed) 
	{
		this.proxyed = proxyed;
	}
	
	public   invoke(  proxy, Method method,  [] args) 
			throws Throwable 
	{
		System.out.println(method.getName() + \" before\");
		return method.invoke(proxyed, args);
	}
}

测试类:

public class Test 
{
	public static void main(String[] args) 
	{
		Person person = new Student();
		ClassLoader pers er = Person.class.getClassLoader();
		Class<?>[] interfaces = new Class[] { Person.class };
		InvocationHandler personProxyHandler = new PersonProxyHandler(person);
		
		Person proxy = (Person) Proxy.newProxyInstance(pers er, interfaces, personProxyHandler);
		
		proxy.study();
		proxy.eat();
	}
}

打印结果:
study before
三和小钢炮study java
eat before
三和小钢炮eat

这里运用了newProxyInstance这个类

public static   newProxyInstance(
ClassLoader loader, 
Class<?>[] interfaces,
InvocationHandler h) throws IllegalArgumentException
{
}

newProxyInstance,方法有三个参数:
loader: 用哪个类加载器去加载代理对象
interfaces:动态代理类需要实现的接口
h:动态代理方法在执行时,会调用h里面的invoke方法去执行

收藏 打印