• 知乎上看到的关于类.class,对象.getClass


     1 public class TestDemo {
     2     //测试
     3     @Test
     4     public void fun01() {
     5         TestDemo q=new TestDemo();
     6         A a = new A();
     7         q.adapter(a);
     8     }
     9     
    10     private void adapter(Base base){
    11                 
    12         HashMap<Class<? extends Base>,String> class2methodName=new HashMap<Class<? extends Base>,String>() 
    13         {
    14             private static final long serialVersionUID = 1L;
    15             {
    16                 put(A.class,"printA");
    17                 put(B.class,"printB");
    18             }
    19         };
    20         System.out.println(class2methodName.get(base.getClass()));
    21         invokeMethod(this,class2methodName.get(base.getClass()),new Class<?>[]{Base.class},new Object[]{base});
    22     }
    23     
    24     public void printA(Base base) {
    25         A a=(A)base;
    26         System.out.println("is A:"+a.num);
    27     }
    28     public void printB(Base base) {
    29         B b=(B)base;
    30         System.out.println("is B:"+b.num);
    31     }
    32     
    33     @SuppressWarnings("unchecked")
    34     private static <T> T invokeMethod(T obj, String methodName, Class<?>[] classes, Object[] objects) {
    35         T val = null;
    36         try {
    37             Method m = null;
    38             if(objects != null && classes != null){
    39                 m = obj.getClass().getDeclaredMethod(methodName, classes);
    40                 val = (T)m.invoke(obj, objects);
    41             }else{
    42                 m = obj.getClass().getDeclaredMethod(methodName);
    43                 val = (T)m.invoke(obj);
    44             }
    45         } catch (Exception e) {
    46             e.printStackTrace();
    47         }
    48         return val;
    49     }
    50 
    51     private class Base{
    52         public int num = 1;
    53     }
    54     
    55     private class A extends Base{
    56         public int num = 2;
    57     }
    58     
    59     private class B extends Base{
    60         public int num = 3;
    61     }
    62 }

    见知乎 : https://www.zhihu.com/question/66705139   也有大佬的点评

    上述代码第21行 : 

    invokeMethod(this,class2methodName.get(base.getClass()),new Class<?>[]{Base.class},new Object[]{base});
    改成:
    invokeMethod(this,class2methodName.get(base.getClass()),new Class<?>[]{base.getClass},new Object[]{base});
    就会报错,NoSuchMethodException
    原因是什么?
      首先看,map中有两个值,一个是{key:运行时类A,value:"printA"}{key:"运行时类B",value:"printB"}
      测试方法中传的是A的对象
      没改的情况 : invokeMethod(testDemo对象,"printA",运行时类A,数组存放的一个A对象)
      改后的情况 : invokeMethod(testDemo对象,"printA",运行时类Base,数组存放的一个A对象)
      
      最后执行的 invokeMethod方法中的,obj.getClass().getDeclaredMethod方法时 会出问题
      
    public void printA(Base base) {
            A a=(A)base;
            System.out.println("is A:"+a.num);
        }
    仔细看,此方法 一个参数Base base,反射的invoke方法要求我们必须是Base对象..

      

     
  • 相关阅读:
    DevNet网站上线
    .net 开发框架(一)[数据通用层]
    发布.NET 开发工具 DevNet4.0.2 开发框架 Maper 映射
    .net 开发框架(二) [实体层与ScriptQuery类]
    SpringDataJPA中使用EntityManager操作返回多表连接结果集
    S3 Bucket object copy
    【Spring】RestTemplateが投げる例外クラスまとめ
    【MySQL】Geometry型を使って地点間の距離を求める
    about mvn license
    springboot配置MappingJackson2HttpMessageConverter最佳实践
  • 原文地址:https://www.cnblogs.com/liyong888/p/7688390.html
Copyright © 2020-2023  润新知