知乎上看到的关于类.class,对象.getClass
public class TestDemo {
//测试
@Test
public void fun01() {
TestDemo q=new TestDemo();
A a = new A();
q.adapter(a);
}
private void adapter(Base base){
HashMap<Class<? extends Base>,String> class2methodName=new HashMap<Class<? extends Base>,String>()
{
private static final long serialVersionUID = 1L;
{
put(A.class,"printA");
put(B.class,"printB");
}
};
System.out.println(class2methodName.get(base.getClass()));
invokeMethod(this,class2methodName.get(base.getClass()),new Class<?>[]{Base.class},new Object[]{base});
}
public void printA(Base base) {
A a=(A)base;
System.out.println("is A:"+a.num);
}
public void printB(Base base) {
B b=(B)base;
System.out.println("is B:"+b.num);
}
@SuppressWarnings("unchecked")
private static <T> T invokeMethod(T obj, String methodName, Class<?>[] classes, Object[] objects) {
T val = null;
try {
Method m = null;
if(objects != null && classes != null){
m = obj.getClass().getDeclaredMethod(methodName, classes);
val = (T)m.invoke(obj, objects);
}else{
m = obj.getClass().getDeclaredMethod(methodName);
val = (T)m.invoke(obj);
}
} catch (Exception e) {
e.printStackTrace();
}
return val;
}
private class Base{
public int num = 1;
}
private class A extends Base{
public int num = 2;
}
private class B extends Base{
public int num = 3;
}
}
见知乎 : 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对象..
知乎上看到的关于类.class,对象.getClass的更多相关文章
- 你好,C++(38)从问题描述中发现对象的属性和行为 6.4 工资程序成长记:类与对象(上)
6.4 工资程序成长记:类与对象 “夜半三更哟,盼天明:寒冬腊月哟,盼春风.若要盼得哟,涨工资,岭上……”自从上次老板许诺给小陈涨工资以后,一转眼又过去几个月了,可是涨工资的事一点动静都没有.小陈只 ...
- Java知多少(7)类与对象
Java是一门面向对象的编程语言,理解Java,首先要理解类与对象这两个概念. Java中的类可以看做C语言中结构体的升级版.结构体是一种构造数据类型,可以包含不同的成员(变量),每个成员的数据类型可 ...
- Java知多少(99)Graphics2D类的绘图方法
Java语言在Graphics类提供绘制各种基本的几何图形的基础上,扩展Graphics类提供一个Graphics2D类,它拥用更强大的二维图形处理能力,提供.坐标转换.颜色管理以及文字布局等更精确的 ...
- Android-通知栏上的RemoteView
Android-通知栏上的RemoteView 学习自 <Android开发艺术探索> https://developer.android.google.cn/reference/andr ...
- 在知乎上看到 Web Socket这篇文章讲得确实挺好,从头看到尾都非常形象生动,一口气看完,没有半点模糊,非常不错
在知乎上看到这篇文章讲得确实挺好,从头看到尾都非常形象生动,一口气看完,没有半点模糊,非常不错,所以推荐给大家,非常值得一读. 作者:Ovear链接:https://www.zhihu.com/que ...
- FTP上传-封装工具类
import java.io.File; import java.io.FileInputStream; import java.io.FileNotFoundException; import ja ...
- 实现Square类,让其继承自Rectangle类,并在Square类增添新属性和方法,在2的基础上,在Square类中重写Rectangle类中的初始化和打印方法
实现Square类,让其继承自Rectangle类,并在Square类增添新属性和方法,在2的基础上,在Square类中重写Rectangle类中的初始化和打印方法 #import <Found ...
- Google 内部代码是不支持异常(Excepton)的,C++ 异常的优劣之处有许多讨论(知乎上的讨论)
最近 Google 开源了其内部多年使用的 C++ 代码库 Abseil 作为 C++ 标准库的补充,并会对其进行持续更新,本文对其进行简要介绍. 一句话概括,这个库的特点是用 C++ 11 的代码实 ...
- ftp上传下载工具类
package com.taotao.utils; import java.io.File; import java.io.FileInputStream; import java.io.FileNo ...
随机推荐
- BMC手册 — 第一模块 BMC介绍
BMC的监控 其实是BPPM与 Patrol 产品的结合.早期它们二个是单独监控产品,后来BPPM被BMC收购.拿来与patrol产口集成产品整合后,BPPM主要用来做展示与告警处理,底层采集采用pa ...
- 超详细的CentOS7 64位下MySQL5.7安装与配置(YUM)【转发+新创】
安装环境:CentOS7 64位 MINI版,安装MySQL5.7 1.配置YUM源 在MySQL官网中下载YUM源rpm安装包:http://dev.mysql.com/downloads/repo ...
- 在Eclipse中如何关联源代码
我们就以Struts2框架为例,展示在Eclipse中如何关联源代码.例如,在Struts2框架的学习中,我们有时需要查看ActionSupport这个类的源码,这个时候就要在Eclipse中关联源代 ...
- 《代码大全(第二版)》【PDF】下载
<代码大全(第二版)>[PDF]下载链接: https://u253469.pipipan.com/fs/253469-230382264 内容简介 <代码大全(第2版)>是著 ...
- TCP/IP的那些事--子网掩码
当前互联网使用的主要是IPv4协议,它是第一个被广泛使用,构成现今互联网的基础的协议.但是,随着用户数量的增多,IPv4包含的IP资源在不断减少.或许你会想,不是还有IPv6吗?IPv6的容量足以应付 ...
- 面试题汇总--数据储存/应用程序/UI控件/客户端的安全性与框架处理。。。
一 数据储存 1.如果后期需要增加数据库中的字段怎么实现,如果不使用 CoreData 呢?编写 SQL 语句来操作原来表中的字段1)增加表字段ALTER TABLE 表名 ADD COLUMN 字 ...
- iOS知识点、面试题 之二
最近面试,与大家分享一下,分三文给大家: 当然Xcode新版本区别,以及iOS新特性 Xcode8 和iOS 10 在之前文章有发过,感兴趣的可以查阅: http://www.cnblogs.com/ ...
- 程序员的自我救赎---10.1:APP版本控制系统
<前言> (一) Winner2.0 框架基础分析 (二)PLSQL报表系统 (三)SSO单点登录 (四) 短信中心与消息中心 (五)钱包系统 (六)GPU支付中心 (七)权限系统 (八) ...
- My Go Resolutions for 2017(from Russ cox's blog)
我的2017年Go决议 一年之季始于春,我认为写一些今年我希望在Go上做的东西是有意义的. 我每年的目标是帮助Go开发人员.我想确保我们在Go团队中所做的工作对Go开发者有重大的积极影响.可能听起来很 ...
- 为clang添加中文关键字
原址: https://zhuanlan.zhihu.com/p/31158537 以clang为基础做了一个与C++.C兼容中英文关键字的编译器 swizl/cnlang 原理就是加与英文关键字等效 ...