黑马程序员技术交流社区

标题: 代理类Proxy疑问 [打印本页]

作者: 菠萝鱼    时间: 2014-2-19 10:37
标题: 代理类Proxy疑问
                        //定义一个ArrayList类型的常量
                        final ArrayList target = new ArrayList();
                       
                        List proxy = (List)Proxy.newProxyInstance(
                        List.class.getClassLoader(),//得到类加载器
                        ArrayList.class.getInterfaces(),
                        new InvocationHandler() {
                        public Object invoke(Object proxy, Method method, Object[] args)
                        throws Throwable {
                                long beginTime = System.currentTimeMillis();//得到当前时间
                                Thread.sleep(10);
                                Object reVal = method.invoke(target, args);
                                long endTime = System.currentTimeMillis();//得到当前时间
                                //输出
                                System.out.println(method.getName()+" runing time is "+(endTime-beginTime));
                                return reVal;
                        }

               
                        });      
代理类是怎么回事,能把上面的代码解释下吗?  


作者: 也,许。    时间: 2014-2-19 15:13
如果需要为已有的实现相同接口的多个类的方法添加一些系统功能,就可以使用代理类,例如,你希望为ArrayList的方法添加一个求方法运行时间的功能,就可以使用动态代理类。因为你希望生成的代理类和ArrayList的功能是一样的,因此,你应该使用和该类一直的类加载器和实现相同的接口才可以。invoke方法中存放的是系统功能的代码,例如你使用ArrayList的添加功能,它就会去调用invoke方法,来运行invoke方法中的系统功能代码。
我也不清楚你哪里不太理解,所以就大概说了一下我的理解,希望可以帮到你。
作者: 李金中    时间: 2014-2-19 15:26
本帖最后由 李金中 于 2014-2-19 15:27 编辑

通过Proxy.newProxyInstance,你得到一个代理类的实例,比如上面代码的就是proxy。
拿代理的一个方法说明流程吧。比如你调用proxy.add();
它就会调用invocationhandler的invoke方法,里面的method传递的就是目标类即List的add对应的method。
所以你通过调用proxy.add()实际上就是调用了list.add()方法,当然是通过反射即invoke。至于怎么实现这一套的,你应该能推测出吧,通过反射机制,可以琢磨出来。
在invocationhandler的invoke方法中,上面的代码在真正调用method.invoke时(即目标对象的add方法),加入了自己的功能,就是计算时间的那个,不就实现了代理的意义么。。。就是可以添加自己想要的功能,还能动态调用目标类的功能。
作者: 菠萝鱼    时间: 2014-2-24 16:20
谢谢同学们




欢迎光临 黑马程序员技术交流社区 (http://bbs.itheima.com/) 黑马程序员IT技术论坛 X3.2