Java入门系列(十二)Java反射
Why--指的是为什么做这件事,也既事物的本质。
反射之中包含了一个“反”的概念,所以要想解释反射就必须先从“正”开始解释,一般而言,当用户使用一个类的时候,应该先知道这个类,而后通过这个类产生实例化对象,但是“反”指的是通过对象找到类。
package cn.mf.demo4; public class Person {
public String name;
private int age; public Person() {
} public Person(String name, int age) {
this.name = name;
this.age = age;
} public void eat() {
System.out.println("人吃饭");
} public void sleep() {
System.out.println("人在睡觉");
} public void playGame() {
System.out.println("人在打游戏");
} public String getName() {
return name;
} public void setName(String name) {
this.name = name;
} public int getAge() {
return age;
} public void setAge(int age) {
this.age = age;
} public String toString() {
return "Person [name=" + name + ", age=" + age + "]";
}
}
Person
@Test
public void function1() {
Person p = new Person() ; //正着操作
Class<?> c = p.getClass();//反着来
System.out.println(c.getName());
}
对于对象的实例化操作,除了使用关键字new之外又多了一个反射机制操作,而且这个操作要比之前使用的new复杂一些,可是有什么用?
对于程序的开发模式之前一直强调:尽量减少耦合,而减少耦合的最好做法是使用接口,但是就算使用了接口也逃不出关键字new,所以实际上new是造成耦合的关键元凶。
我们以传统的工厂模式为例,看看存在的问题
IBaoCaiMing 报菜名接口
package cn.mf.demo; public interface IBaoCaiMing {
public void BaoCaiMing();
}
ZhengXiongZhang 蒸熊掌实现报菜名
package cn.mf.demo; public class ZhengXiongZhang implements IBaoCaiMing{ @Override
public void BaoCaiMing() {
System.out.println("蒸熊掌");
} }
ZhengYaoGao蒸羊羔实现报菜名
package cn.mf.demo; public class ZhengYaoGao implements IBaoCaiMing { @Override
public void BaoCaiMing() {
System.out.println("蒸羊羔");
} }
然后,我们实现一个静态的工厂方法,在这个工厂类中,静态地得到报菜名的实例
public class Factory {
public static IBaoCaiMing ZhengXiongZhang() {
return new ZhengXiongZhang();
} public static IBaoCaiMing ZhengYaoGao() {
return new ZhengYaoGao();
}
}
此时,如果我们把蒸鹿尾儿、烧花鸭、烧雏鸡、烧子鹅。。。。。。一百多道菜都添加进去,我们就需要修改一百多次工厂类。麻烦的一笔!
但是如果使用反射机制修改工厂模式就可以很好的解决以上问题,代码修改如下:
public class Factory {
public static IBaoCaiMing getInstance(String className) {
IBaoCaiMing bcm = null;
try {
bcm = (IBaoCaiMing) Class.forName(className).newInstance();
} catch (Exception e) {
e.printStackTrace();
}
return bcm;
}
}
调用(有木有发现随便增加菜名,Factory压根就不用做任何修改,可谓以不变应万变)
@Test
public void BaoCaiMingTest() {
IBaoCaiMing bcm1 = Factory.getInstance("cn.mf.demo.ZhengXiongZhang") ;
bcm1.BaoCaiMing() ;
IBaoCaiMing bcm2 = Factory.getInstance("cn.mf.demo.ZhengYaoGao") ;
bcm2.BaoCaiMing() ;
}
How--指的是怎样去做一件事,也就是做事的方法、方式。
Java的反射机制的实现要借助于4个类:class,Constructor,Field,Method;
其中class代表的时类对 象,Constructor-类的构造器对象,Field-类的属性对象,Method-类的方法对象。通过这四个对象我们可以粗略的看到一个类的各个组 成部分。
1、得到构造器的方法
Constructor getConstructor(Class[] params) -- 获得使用特殊的参数类型的公共构造函数, Constructor[] getConstructors() -- 获得类的所有公共构造函数 Constructor getDeclaredConstructor(Class[] params) -- 获得使用特定参数类型的构造函数(与接入级别无关) Constructor[] getDeclaredConstructors() -- 获得类的所有构造函数(与接入级别无关)
2、获得字段信息的方法
Field getField(String name) -- 获得命名的公共字段 Field[] getFields() -- 获得类的所有公共字段 Field getDeclaredField(String name) -- 获得类声明的命名的字段 Field[] getDeclaredFields() -- 获得类声明的所有字段
3、获得方法信息的方法
Method getMethod(String name, Class[] params) -- 使用特定的参数类型,获得命名的公共方法 Method[] getMethods() -- 获得类的所有公共方法 Method getDeclaredMethod(String name, Class[] params) -- 使用特写的参数类型,获得类声明的命名的方法 Method[] getDeclaredMethods() -- 获得类声明的所有方法
继续思考中。。。回头继续完善。。。
Java入门系列(十二)Java反射的更多相关文章
- java se系列(十二)集合
1.集合 1.1.什么是集合 存储对象的容器,面向对象语言对事物的体现,都是以对象的形式来体现的,所以为了方便对多个对象的操作,存储对象,集合是存储对象最常用的一种方式.集合的出现就是为了持有对象.集 ...
- java入门学习(十二)运算语句 if switch
这两天在网上做兼职,耽误了些博客见谅哈 欢迎来我的博客:www.taomaipin.com java中的运算语句而且频繁用到的无法就是条件语句和循环语句,包括if,for,while,switch,b ...
- Java入门系列(二)Java常用关键字
53个关键字 在JAVA中目前一共有53个关键字:其中由51+2个保留字=53个关键字 访问控制 private protected public default 类.方法和 ...
- Java入门教程十二(集合与泛型)
在 Java 中数组的长度是不可修改的.然而在实际应用的很多情况下,无法确定数据数量.这些数据不适合使用数组来保存,这时候就需要使用集合. Java 的集合就像一个容器,用来存储 Java 类的对象. ...
- 菜鸡的Java笔记 第二十二 - java 对象多态性
本次只是围绕着多态性的概念来进行讲解,但是所讲解的代码与实际的开发几乎没有关系,而且多态一定是在继承性的基础上才可以操作的, 而本次将使用类继承的关系来描述多态的性质,实际的开发中不会出 ...
- Java进阶(四十二)Java中多线程使用匿名内部类的方式进行创建3种方式
Java中多线程使用匿名内部类的方式进行创建3种方式 package cn.edu.ujn.demo; // 匿名内部类的格式: public class ThreadDemo { public st ...
- Java 读书笔记 (十二) Java Character 类
在实际开发过程中, 我们经常会遇到需要使用对象,而不是内置数据类型的情况. 为了解决这个问题, Java语言为内置数据类型char提供了包装类Character类. 可以使用Character的构造方 ...
- Java学习笔记十二:Java中方法的重载
Java中方法的重载 什么是方法的重载呢? 如果同一个类中包含了两个或两个以上方法名相同.方法参数的个数.顺序或类型不同的方法,则称为方法的重载,也可称该方法被重载了.如下所示 4 个方法名称都为 s ...
- 菜鸡的Java笔记 第十二 - java 构造方法与匿名对象
1.点 构造方法的作用以及定义要求 匿名对象的使用 构造方法: 只要出现()的都表示方法 构造方法就是类构造对象时调用的方法,主要用来实例化对象.> ...
- Java 设计模式系列(二十)状态模式
Java 设计模式系列(二十)状态模式 状态模式,又称状态对象模式(Pattern of Objects for States),状态模式是对象的行为模式.状态模式允许一个对象在其内部状态改变的时候改 ...
随机推荐
- Java多线程之原子性 volatile、atomicInteger测试
原文链接:http://www.cnblogs.com/zhengbin/p/5653051.html 一.补充概念 1.什么是线程安全性? <Java Concurrency in Pract ...
- html 文档类型
<!doctype>用来声明html的版本,浏览器只有知道html的版本后才能正确显示文档,<!DOCTYPE>本身不是一个标签,而是一个声明.
- vander范德蒙德行列式
https://baike.baidu.com/item/%E8%8C%83%E5%BE%B7%E8%92%99%E8%A1%8C%E5%88%97%E5%BC%8F function m=vande ...
- 构建squid代理服务器
基本概念 本文使用squid代理服务 软件介绍:百度百科 作为应用层的代理服务软件,Squid主要提供缓存加速.应用层过滤控制的功能: 工作机制:缓存网页对象,减少重复请求(HTTP代理的缓存加速对象 ...
- BZOJ5249 九省联考2018IIIDX(线段树+贪心)
显然这形成了一个树形结构.考虑这样一种贪心:按照曲目顺序,每次取消其父亲的预留,并选择当前可选择(保证其子树有合法选择且满足预留)的最大值,然后对其子树预留出大于等于他的一些值.这个做法显然是正确的. ...
- EF 跨库查询
原因:最近公司项目,遇到一个ef跨库查询的问题.(只是跨库,并不是跨服务器哈) 主要我们的一些数据,譬如地址,城市需要查询公共资料库. 但是本身我的程序设计采用的是ef框架的.因此为这事花费了1天时间 ...
- MT【61】含参数二次函数最大最小值
评:此类题目在高考中作为压轴题也曾考过,一般通性通法都如上面的做法,但是我们如果可以站在包络的角度,很多问题将变得很清晰:
- Spring Security和 JWT两大利器来打造一个简易的权限系统。
写在前面 关于 Spring Security Web系统的认证和权限模块也算是一个系统的基础设施了,几乎任何的互联网服务都会涉及到这方面的要求.在Java EE领域,成熟的安全框架解决方案一般有 A ...
- Stack Overflow:研究发现访问PHP和 Android的流量更可能来自低收入国家
Stack Overflow 的数据科学家 David Robinson 发现,软件行业的分工让不同发达地区的程序员依赖于不同的编程语言.软件已经是一个全球性的行业,也有高端低端之分,最高端的是数据 ...
- OpenAI 开源机器人模拟 Python 库,并行模拟处理速度提升400%
10000da.cnvboyule.cnjiaeidaypt.cn 在过去一年的研究中,OpenAI团队开源一个使用 MuJoCoengine开发的用于机器人模拟的高性能Python库.雷锋网了解到 ...