黑马程序员技术交流社区

标题: 代理引发的问题,你知道答案么? [打印本页]

作者: 沈文杰    时间: 2013-3-14 11:05
标题: 代理引发的问题,你知道答案么?
本帖最后由 沈文杰 于 2013-3-14 16:27 编辑
  1. import java.lang.reflect.Constructor;
  2. import java.lang.reflect.InvocationHandler;
  3. import java.lang.reflect.Method;
  4. import java.lang.reflect.Proxy;
  5. import java.util.Collection;


  6. /**
  7. *Proxy 提供用于创建动态代理类和实例的静态方法,它还是由这些方法创建的所有动态代理类的超类。  
  8. * 2013年3月14日08:57:25
  9. *
  10. */

  11. public class ProxyTest {

  12.         /**
  13.          * @param args
  14.          */
  15.         public static void main(String[] args)throws Exception {
  16.                 // TODO Auto-generated method stub
  17.                 //如何创建一个代理类,
  18.                 Class clazzProxy1 =
  19.                         Proxy.getProxyClass(Collection.class.getClassLoader(),Collection.class.getInterfaces());
  20.                 System.out.println(clazzProxy1.getName());
  21.                
  22.                 System.out.println("----------begin constructors list:-----------");
  23.                 printConstructor(clazzProxy1);
  24.                 /**
  25.                  * $Proxy0表示无参构造方法
  26.                  * $Proxy0(InvocationHandler,int)//表示有参构造方法
  27.                  */        
  28.                
  29.                 System.out.println("-------------begin methods list----------------");
  30.                 printmethods(clazzProxy1);

  31.         }

  32.         private static void printmethods(Class clazzProxy1) {
  33.                 Method[] Methods = clazzProxy1.getMethods();
  34.                 for(Method method : Methods){
  35.                         String name = method.getName();
  36.                         StringBuilder sBuilder = new StringBuilder(name);
  37.                         sBuilder.append("(");
  38.                         Class[] clazzParameters = method.getParameterTypes();
  39.                         for(Class clazzParameter : clazzParameters){
  40.                                 sBuilder.append(clazzParameter.getName()).append(",");
  41.                         }
  42.                         if(clazzParameters!=null&&clazzParameters.length!=0)
  43.                                 sBuilder.deleteCharAt(sBuilder.length()-1);
  44.                         sBuilder.append(")");
  45.                         System.out.println(sBuilder.toString());
  46.                 }
  47.                
  48.         }

  49.         private static void printConstructor(Class clazzProxy1)throws Exception {
  50.                 // TODO Auto-generated method stub
  51.                 Constructor[] constructors = clazzProxy1.getConstructors();
  52.                 for(Constructor constructor : constructors){
  53.                         String name = constructor.getName();
  54.                         StringBuilder sBuilder = new StringBuilder(name);
  55.                         sBuilder.append("(");
  56.                         Class[] clazzParameters = constructor.getParameterTypes();
  57.                         for(Class clazzParameter : clazzParameters){
  58.                                 sBuilder.append(clazzParameter.getName()).append(",");
  59.                         }
  60.                         if(clazzParameters!=null&&clazzParameters.length!=0)
  61.                                 sBuilder.deleteCharAt(sBuilder.length()-1);
  62.                         sBuilder.append(")");
  63.                         System.out.println(sBuilder.toString());
  64.                 }
  65.                 System.out.println("-------------begin create new object instance----------------");
  66.                 //Object obj = clazzProxy1.newInstance();
  67.                
  68.                 Constructor constructor = clazzProxy1.getConstructor(InvocationHandler.class);
  69.                 class MyInvocationHandler1 implements InvocationHandler {
  70.                         
  71.                         @Override
  72.                         public Object invoke(Object proxy, Method method, Object[] args)
  73.                                         throws Throwable {
  74.                                 // TODO Auto-generated method stub
  75.                                 return null;
  76.                         }
  77.                 }
  78.                 Collection proxy1 = (Collection)constructor.newInstance(new MyInvocationHandler1());
  79. System.out.println(proxy1);

  80.         }

  81. }
复制代码
写代码的时候不小心将Class clazzProxy1 =
                        Proxy.getProxyClass(Collection.class.getClassLoader(),Collection.class);
写成了Class clazzProxy1 =
                        Proxy.getProxyClass(Collection.class.getClassLoader(),Collection.class.getInterfaces());
运行结果前面的打印动态代理中的构造函数和一般方法都没出错,到最后new对象出现了问题,求解?
将最后的new对象改成如下格式后又正确了,什么情况?
                Object v = (Object)constructor.newInstance(new MyInvocationHandler1());
                System.out.println(v);
作者: 谢洋    时间: 2013-3-14 12:07
import java.lang.reflect.Constructor;
import java.lang.reflect.InvocationHandler;
import java.lang.reflect.Method;
import java.lang.reflect.Proxy;
import java.util.Collection;

/**
*Proxy 提供用于创建动态代理类和实例的静态方法,它还是由这些方法创建的所有动态代理类的超类。  
* 2013年3月14日08:57:25
*
*/
public class ProxyTest {
        /**
         * @param args
         */
        public static void main(String[] args)throws Exception {
                // TODO Auto-generated method stub
                //如何创建一个代理类,
                Class clazzProxy1 =//Collection.class.getInterfaces(),得到是Iterator接口的class数组,
                                          //那为什么要这么Classes?该方法正是利用这些接口组得到对应代理类的Class,
                                          //那用Collection.class和Collection.class.getInterfaces()生成代理类Class有什么不同?
                                          //因为Iterator,是Collection的父接口,所以所生成的代理类的方法比后者要多,我们可以测试methods的长度得到验证
                      Proxy.getProxyClass(Collection.class.getClassLoader(),Collection.class.getInterfaces());
                System.out.println(clazzProxy1.getName());
               
                System.out.println("----------begin constructors list:-----------");
                printConstructor(clazzProxy1);
                /**
                 * $Proxy0表示无参构造方法
                 * $Proxy0(InvocationHandler,int)//表示有参构造方法
                 */        
               
                System.out.println("-------------begin methods list----------------");
                printmethods(clazzProxy1);
        }
        private static void printmethods(Class clazzProxy1) {
                Method[] Methods = clazzProxy1.getMethods();
                for(Method method : Methods){
                        String name = method.getName();
                        StringBuilder sBuilder = new StringBuilder(name);
                        sBuilder.append("(");
                        Class[] clazzParameters = method.getParameterTypes();
                        for(Class clazzParameter : clazzParameters){
                                sBuilder.append(clazzParameter.getName()).append(",");
                        }
                        if(clazzParameters!=null&&clazzParameters.length!=0)
                                sBuilder.deleteCharAt(sBuilder.length()-1);
                        sBuilder.append(")");
                        System.out.println(sBuilder.toString());
                }
               
        }
        private static void printConstructor(Class clazzProxy1)throws Exception {
                // TODO Auto-generated method stub
                Constructor[] constructors = clazzProxy1.getConstructors();
                for(Constructor constructor : constructors){
                        String name = constructor.getName();
                        StringBuilder sBuilder = new StringBuilder(name);
                        sBuilder.append("(");
                        Class[] clazzParameters = constructor.getParameterTypes();
                        for(Class clazzParameter : clazzParameters){
                                sBuilder.append(clazzParameter.getName()).append(",");
                        }
                        if(clazzParameters!=null&&clazzParameters.length!=0)
                                sBuilder.deleteCharAt(sBuilder.length()-1);
                        sBuilder.append(")");
                        System.out.println(sBuilder.toString());
                }
                System.out.println("-------------begin create new object instance----------------");
                //Object obj = clazzProxy1.newInstance();
               
                Constructor constructor = clazzProxy1.getConstructor(InvocationHandler.class);
                class MyInvocationHandler1 implements InvocationHandler {
                        
                        @Override
                        public Object invoke(Object proxy, Method method, Object[] args)
                                        throws Throwable {
                                // TODO Auto-generated method stub
                                return null;
                        }
                }
                //因为上面得到是Iterator接口的class数组,生成是Collection父类的接口的代理类,那当然不能向下转型为(Collection),可以试下转为Iterator看看
               Collection proxy1 = (Collection)constructor.newInstance(new MyInvocationHandler1());
System.out.println(proxy1);

        }
}





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