关于动态代理的那些事 (JDK的动态代理)有3个接口,分别为ProxyInter1,ProxyInter2,ProxyInter3,但是接口2继承接口3public interface ProxyInter1{
void func();
}public interface ProxyInter2 extends ProxyInter3{
void run();
}public interface ProxyInter3 {
void sun();
}下面这个是被代理的类,实现了ProxyInter1,ProxyInter2两个接口public class ProxyImp implements ProxyInter1,ProxyInter2{
@Override
public void func() {
System.out.println("This is function");
}
@Override
public void run() {
System.out.println("This is run");
}
@Override
public void sun() {
System.out.println("This is sun");
}
}下面这个是代理的类的执行:public class MyProxy {
public static void main(String[] args) throws Exception {
ProxyInter1 proxyInter1 = new ProxyImp();
ProxyInter2 proxyInter2 = new ProxyImp();
ProxyInter3 proxyInter3 = new ProxyImp();
ProxyInter3 pInter = (ProxyInter3) Proxy.newProxyInstance
(proxyInter1.getClass().getClassLoader(), proxyInter1.getClass().getInterfaces(),new InvocationHandler(){
@Override
public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
System.out.println("这是代理之前的事情");
Object object = method.invoke(proxyInter1,args);
System.out.println("这是代理之后的事情");
return object;
}
});
// pInter.func();
pInter.sun();
}
}我的疑问是:1、ProxyInter1,ProxyInter3只是两个接口,没有任何关系,invoke方法里面传的参数为proxyInter1对象,但是上面Proxy.newProxyInstance返回类型为什么是ProxyInter3的类型,却不是ProxyInter1类型的,而且调用的方法只能是ProxyInter3的方法,不能调用ProxyInter1的,2、在Proxy.newProxyInstance方法中,按常理说,调用被代理类的类加载器,被代理类的接口(Interfaces),但是,里面写上proxyInter1,proxyInter2,proxyInter3的三种任意一个都不会报错,问题是ProxyInter1 和ProxyInter2个接口没有任何关系,运行出来一样不会报错,这是什么原因?麻烦各位大佬帮我解答下,让我这个小白涨涨知识。。。。。
1 回答
已采纳
HansonQ
TA贡献223条经验 获得超56个赞
//1、第一个问题你生成的代理对象是给ProxyInter1这个目标对象,但是你却强转为ProxyInter3,这个newProxyInstance方法的返回值是一个Object.既然是另一个对象当然不能调用别的对象方法 //2、第二个我之间诶写的代码 public class MyProxy { public static void main(String[] args) { final ProxyInter1 proxyInter1 = new ProxyImp(); ProxyInter2 proxyInter2 = new ProxyImp(); ProxyInter3 proxyInter3 = new ProxyImp(); /** * Proxy.newProxyInstance * 参数1:loader,类加载器,动态代理类 运行时创建,任何类都需要类加载器将其加载到内存当中 * 要求:传递的是被代理的类加载器ClassLoader(非必须) * 类加载器怎样获取? * 一般情况下:当前类.class.getClassLoader获取加载器 * 目标类实例.getClass().getClassLoader获取加载器 * 参数2:Class[] interfaces:代理类需要实现的所有接口 * 要求:得到被代理对象所实现的接口的所有Class对象 * 方式1:目标类实例.getClass().getInterfaces();注意只能获得自己的接口,不能获得父元素接口 * 方式2:new Class[]{UserService.class} * 例如:jdbc驱动-->DriverManager 获得接口Connection * 参数3:InvocationHandler 处理类,接口,必须进行实现,一般采用匿名内部类 * 提供了一个invoke方法,代理类的每一个方法执行时,都将调用一次invoke * 参数 3.1、Object proxy:代理对象 * 参数 3.2、Method method:代理对象当前执行的方法的描述对象(反射) * 参数 3.3、Object[] args:方法的实际参数 */ ProxyInter1 inter1 = (ProxyInter1) Proxy.newProxyInstance(MyProxy.class.getClassLoader(), proxyInter1.getClass().getInterfaces(), new InvocationHandler() { @Override public Object invoke(Object proxy, Method method, Object[] args) throws Throwable { System.out.println("call method before ..."); Object object = method.invoke(proxyInter1, args); System.out.println("call method after ..."); return object; } }); inter1.func(); } }
添加回答
举报
0/150
提交
取消