java反射使用实例
2017-03-26 18:43
148 查看
最近项目中用到了很多java反射机制,在阅读一些jar源码的过程中也发现了好多对于反射的使用,很经典。因此对其使用做了一些梳理,讲解直接注释在代码中。代码讲解的内容为基础使用。还有一部分是在项目中的使用还在总结中。
public interface B {
}
public interface B2 {
}
public class Book implements B,B2{
private String name;
private int pageNums;
private Double price;
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public int getPageNums() {
return pageNums;
}
public void setPageNums(int pageNums) {
this.pageNums = pageNums;
}
public Double getPrice() {
return price;
}
public void setPrice(Double price) {
this.price = price;
}
@Override
public String toString() {
// TODO Auto-generated method stub
return "name: " + this.name + "page: " + pageNums + "price: " + price;
}
}
在类中测试:
package copyTable.wu.copy.util.reflact;
import java.lang.reflect.Field;
import java.lang.reflect.Method;
import java.util.Map;
import org.apache.commons.collections.MapUtils;
public class ReflactTest {
/**
* @Description: TODO(获取类名的三种方法)
* @date 2017年3月23日
*/
public static void main(String[] args) {
// TODO Auto-generated method stub
getClassesBythreeWays();
getMethods();
getFields();
getInterface();
Book book = getInstance();
System.out.println(book.toString());
getInstanceAndFieldEval();
}
@SuppressWarnings("unused")
public static void getClassesBythreeWays(){
try {
/**
* 第一种方法,通过forName()方法获取
*/
Class<?> clazz = Class.forName("copyTable.wu.copy.util.reflact.Book");
System.out.println("第一种方法 :" + clazz.getName());
if(clazz == null){
System.out.println("反射失败。。。");
}
} catch (ClassNotFoundException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
/**
* 第二种方法,通过类名获取
*/
Class<?> clazz = Book.class;
System.out.println("第二种方法: " + clazz.getName());
/**
* 第三种方法,通过getClass方法
*/
// Book book1 = new Book();
// Class<? extends Book> book = book1.getClass(); //第三种方法
Class<?> book = clazz.getClass();
System.out.println("第三种方法: " + book.getName());
}
/**
*
* @Description: TODO(获取对象的所有方法名称)
* @date 2017年3月23日
* 获取到的方法列表:
* getPageNums setPageNums getPrice setPrice getName setName
* (Object的方法)wait wait wait equals toString hashCode getClass notify notifyAll
*/
public static void getMethods(){
Class<?> clazz = Book.class;
Method[] methods = clazz.getMethods();
System.out.println("\n方法列表: ");
for(Method method : methods){
System.out.print(method.getName() + " ");
}
}
//获取构造函数 Constructor<?>[] constructors = class1.getConstructors() ;
/**
* @Description: TODO(获取所有属性)
* @date 2017年3月23日
*/
public static void getFields(){
Class<?> clazz = Book.class;
/**
*getDeclaredFields()获得某个类的所有申明的字段,即包括public、private和proteced
*但是不包括父类的申明字段。
*getFields()获得某个类的所有的公共(public)的字段,包括父类。
*/
Field[] fields = clazz.getDeclaredFields();
System.out.println("\n属性列表: ");
for(Field field : fields){
System.out.print(field.getName() + " ");
}
System.out.println("\n属性的范围: ");
for(Field field : fields){
System.out.println(field);
}
}
/**
* @Description: TODO(获取接口)
* @date 2017年3月23日
*/
public static void getInterface(){
Class<?> clazz = Book.class;
Class<?>[] interfaceList = clazz.getInterfaces();
System.out.println("\n接口列表");
for(Class method : interfaceList){
System.out.print(method.getName() + " ");
}
}
/**
* @Description: TODO(获取实例)
* @date 2017年3月23日
*/
public static Book getInstance(){
Class<?> clazz = Book.class;
try {
Object obj = clazz.newInstance();
return (Book)obj;
} catch (InstantiationException e) {
e.printStackTrace();
} catch (IllegalAccessException e) {
e.printStackTrace();
}
return null;
}
/**
* @Description: TODO(实例化并给属性赋值)
* @date 2017年3月23日
*/
public static void getInstanceAndFieldEval(){
Class<?> clazz = Book.class;
try {
Book book = (Book) clazz.newInstance();
Field field = clazz.getDeclaredField("name");
//由于name属性为private私有变量,所以不能直接访问,需要关闭jdk安全检查
//打破封装 实际上setAccessible是启用和禁用访问安全检查的开关,并不是为true就能访问为false就不能访问
//由于JDK的安全检查耗时较多.所以通过setAccessible(true)的方式关闭安全检查就可以达到提升反射速度的目的
field.setAccessible(true);
field.set(book, "我的书名");
System.out.println("实例化并赋值后的book:"+ book.toString());
Method setName = clazz.getDeclaredMethod("setName", String.class);//String.class表示该setName的参数类型
setName.setAccessible(true);
setName.invoke(book, "我通过获取setName方法后修改的书名");
System.out.println("获取setName方法后修改的book:"+ book.toString());
//获取实例的书名
String name = (String) field.get(book);
System.out.println("通过field获取实例的书名:"+ name);
Method getName = clazz.getDeclaredMethod("getName");
getName.setAccessible(true);
String nameByGetNameMethod = (String) getName.invoke(book);
System.out.println("通过使用Method实例调用getName方法获取的书名:"+ nameByGetNameMethod);
//参数是int的处理,int类型不能使用integer会报错:
Method setPageNums = clazz.getDeclaredMethod("setPageNums", int.class);
setPageNums.setAccessible(true);
setPageNums.invoke(book, 222);
Method getPageNums = clazz.getDeclaredMethod("getPageNums");
getPageNums.setAccessible(true);
Integer pageNum = (Integer) getPageNums.invoke(book);
System.out.println("pageNum: " + pageNum);
//参数是Double的处理:
Method setPrice = clazz.getDeclaredMethod("setPrice", Double.class);
setPrice.setAccessible(true);
setPrice.invoke(book, 222.222);
// Method getPageNums = clazz.getDeclaredMethod("getPageNums", Double.class);
Method getPrice = clazz.getDeclaredMethod("getPrice");
getPrice.setAccessible(true);
// Integer pageNum = (Integer) getPageNums.invoke(book, Integer);
Double price = (Double) getPrice.invoke(book);
System.out.println("price: " + price);
} catch (SecurityException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (Exception e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
//下文总结来自:http://www.cnblogs.com/zhaoyanjun/p/6074887.html
//Constructor getConstructor(Class[] params) 根据构造函数的参数,返回一个具体的具有public属性的构造函数
//Constructor getConstructors() 返回所有具有public属性的构造函数数组
//Constructor getDeclaredConstructor(Class[] params) 根据构造函数的参数,返回一个具体的构造函数(不分public和非public属性)
//Constructor getDeclaredConstructors() 返回该类中所有的构造函数数组(不分public和非public属性)
//-------------------------------------------------------------------------------
//Method getMethod(String name, Class[] params) 根据方法名和参数,返回一个具体的具有public属性的方法
//Method[] getMethods() 返回所有具有public属性的方法数组
//Method getDeclaredMethod(String name, Class[] params) 根据方法名和参数,返回一个具体的方法(不分public和非public属性)
//Method[] getDeclaredMethods() 返回该类中的所有的方法数组(不分public和非public属性)
//-------------------------------------------------------------------------------
//Field getField(String name) 根据变量名,返回一个具体的具有public属性的成员变量
//Field[] getFields() 返回具有public属性的成员变量的数组
//Field getDeclaredField(String name) 根据变量名,返回一个成员变量(不分public和非public属性)
//Field[] getDelcaredField() 返回所有成员变量组成的数组(不分public和非public属性)
/**
* 高级使用法
*/
public static <T> T transMap2Bean(Map<String,Object> props,T t) {
if(MapUtils.isEmpty(props) || t==null){
return t;
}
try {
for(String field : props.keySet()){
Object val=props.get(field);
try {
String methodName=setMethodName(field);
Method method=t.getClass().getMethod(methodName, new Class[] { String.class });
if(method!=null){
method.invoke(t, val);
}
} catch (Exception e) {
}
}
} catch (Exception e) {
e.printStackTrace();
return t;
}
return t;
}
public static String setMethodName(String fieldName){
StringBuffer methodName = new StringBuffer("set");
fieldName = fieldName.toLowerCase();
if(fieldName.indexOf("_") == 0){
methodName.append(fieldName);
}else{
methodName.append(toUpperCaseFirstOne(fieldName));
}
return methodName.toString();
}
//首字母转大写
public static String toUpperCaseFirstOne(String s)
{
if(Character.isUpperCase(s.charAt(0)))
return s;
else
return (new StringBuilder()).append(Character.toUpperCase(s.charAt(0))).append(s.substring(1)).toString();
}
}
public interface B {
}
public interface B2 {
}
public class Book implements B,B2{
private String name;
private int pageNums;
private Double price;
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public int getPageNums() {
return pageNums;
}
public void setPageNums(int pageNums) {
this.pageNums = pageNums;
}
public Double getPrice() {
return price;
}
public void setPrice(Double price) {
this.price = price;
}
@Override
public String toString() {
// TODO Auto-generated method stub
return "name: " + this.name + "page: " + pageNums + "price: " + price;
}
}
在类中测试:
package copyTable.wu.copy.util.reflact;
import java.lang.reflect.Field;
import java.lang.reflect.Method;
import java.util.Map;
import org.apache.commons.collections.MapUtils;
public class ReflactTest {
/**
* @Description: TODO(获取类名的三种方法)
* @date 2017年3月23日
*/
public static void main(String[] args) {
// TODO Auto-generated method stub
getClassesBythreeWays();
getMethods();
getFields();
getInterface();
Book book = getInstance();
System.out.println(book.toString());
getInstanceAndFieldEval();
}
@SuppressWarnings("unused")
public static void getClassesBythreeWays(){
try {
/**
* 第一种方法,通过forName()方法获取
*/
Class<?> clazz = Class.forName("copyTable.wu.copy.util.reflact.Book");
System.out.println("第一种方法 :" + clazz.getName());
if(clazz == null){
System.out.println("反射失败。。。");
}
} catch (ClassNotFoundException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
/**
* 第二种方法,通过类名获取
*/
Class<?> clazz = Book.class;
System.out.println("第二种方法: " + clazz.getName());
/**
* 第三种方法,通过getClass方法
*/
// Book book1 = new Book();
// Class<? extends Book> book = book1.getClass(); //第三种方法
Class<?> book = clazz.getClass();
System.out.println("第三种方法: " + book.getName());
}
/**
*
* @Description: TODO(获取对象的所有方法名称)
* @date 2017年3月23日
* 获取到的方法列表:
* getPageNums setPageNums getPrice setPrice getName setName
* (Object的方法)wait wait wait equals toString hashCode getClass notify notifyAll
*/
public static void getMethods(){
Class<?> clazz = Book.class;
Method[] methods = clazz.getMethods();
System.out.println("\n方法列表: ");
for(Method method : methods){
System.out.print(method.getName() + " ");
}
}
//获取构造函数 Constructor<?>[] constructors = class1.getConstructors() ;
/**
* @Description: TODO(获取所有属性)
* @date 2017年3月23日
*/
public static void getFields(){
Class<?> clazz = Book.class;
/**
*getDeclaredFields()获得某个类的所有申明的字段,即包括public、private和proteced
*但是不包括父类的申明字段。
*getFields()获得某个类的所有的公共(public)的字段,包括父类。
*/
Field[] fields = clazz.getDeclaredFields();
System.out.println("\n属性列表: ");
for(Field field : fields){
System.out.print(field.getName() + " ");
}
System.out.println("\n属性的范围: ");
for(Field field : fields){
System.out.println(field);
}
}
/**
* @Description: TODO(获取接口)
* @date 2017年3月23日
*/
public static void getInterface(){
Class<?> clazz = Book.class;
Class<?>[] interfaceList = clazz.getInterfaces();
System.out.println("\n接口列表");
for(Class method : interfaceList){
System.out.print(method.getName() + " ");
}
}
/**
* @Description: TODO(获取实例)
* @date 2017年3月23日
*/
public static Book getInstance(){
Class<?> clazz = Book.class;
try {
Object obj = clazz.newInstance();
return (Book)obj;
} catch (InstantiationException e) {
e.printStackTrace();
} catch (IllegalAccessException e) {
e.printStackTrace();
}
return null;
}
/**
* @Description: TODO(实例化并给属性赋值)
* @date 2017年3月23日
*/
public static void getInstanceAndFieldEval(){
Class<?> clazz = Book.class;
try {
Book book = (Book) clazz.newInstance();
Field field = clazz.getDeclaredField("name");
//由于name属性为private私有变量,所以不能直接访问,需要关闭jdk安全检查
//打破封装 实际上setAccessible是启用和禁用访问安全检查的开关,并不是为true就能访问为false就不能访问
//由于JDK的安全检查耗时较多.所以通过setAccessible(true)的方式关闭安全检查就可以达到提升反射速度的目的
field.setAccessible(true);
field.set(book, "我的书名");
System.out.println("实例化并赋值后的book:"+ book.toString());
Method setName = clazz.getDeclaredMethod("setName", String.class);//String.class表示该setName的参数类型
setName.setAccessible(true);
setName.invoke(book, "我通过获取setName方法后修改的书名");
System.out.println("获取setName方法后修改的book:"+ book.toString());
//获取实例的书名
String name = (String) field.get(book);
System.out.println("通过field获取实例的书名:"+ name);
Method getName = clazz.getDeclaredMethod("getName");
getName.setAccessible(true);
String nameByGetNameMethod = (String) getName.invoke(book);
System.out.println("通过使用Method实例调用getName方法获取的书名:"+ nameByGetNameMethod);
//参数是int的处理,int类型不能使用integer会报错:
Method setPageNums = clazz.getDeclaredMethod("setPageNums", int.class);
setPageNums.setAccessible(true);
setPageNums.invoke(book, 222);
Method getPageNums = clazz.getDeclaredMethod("getPageNums");
getPageNums.setAccessible(true);
Integer pageNum = (Integer) getPageNums.invoke(book);
System.out.println("pageNum: " + pageNum);
//参数是Double的处理:
Method setPrice = clazz.getDeclaredMethod("setPrice", Double.class);
setPrice.setAccessible(true);
setPrice.invoke(book, 222.222);
// Method getPageNums = clazz.getDeclaredMethod("getPageNums", Double.class);
Method getPrice = clazz.getDeclaredMethod("getPrice");
getPrice.setAccessible(true);
// Integer pageNum = (Integer) getPageNums.invoke(book, Integer);
Double price = (Double) getPrice.invoke(book);
System.out.println("price: " + price);
} catch (SecurityException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (Exception e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
//下文总结来自:http://www.cnblogs.com/zhaoyanjun/p/6074887.html
//Constructor getConstructor(Class[] params) 根据构造函数的参数,返回一个具体的具有public属性的构造函数
//Constructor getConstructors() 返回所有具有public属性的构造函数数组
//Constructor getDeclaredConstructor(Class[] params) 根据构造函数的参数,返回一个具体的构造函数(不分public和非public属性)
//Constructor getDeclaredConstructors() 返回该类中所有的构造函数数组(不分public和非public属性)
//-------------------------------------------------------------------------------
//Method getMethod(String name, Class[] params) 根据方法名和参数,返回一个具体的具有public属性的方法
//Method[] getMethods() 返回所有具有public属性的方法数组
//Method getDeclaredMethod(String name, Class[] params) 根据方法名和参数,返回一个具体的方法(不分public和非public属性)
//Method[] getDeclaredMethods() 返回该类中的所有的方法数组(不分public和非public属性)
//-------------------------------------------------------------------------------
//Field getField(String name) 根据变量名,返回一个具体的具有public属性的成员变量
//Field[] getFields() 返回具有public属性的成员变量的数组
//Field getDeclaredField(String name) 根据变量名,返回一个成员变量(不分public和非public属性)
//Field[] getDelcaredField() 返回所有成员变量组成的数组(不分public和非public属性)
/**
* 高级使用法
*/
public static <T> T transMap2Bean(Map<String,Object> props,T t) {
if(MapUtils.isEmpty(props) || t==null){
return t;
}
try {
for(String field : props.keySet()){
Object val=props.get(field);
try {
String methodName=setMethodName(field);
Method method=t.getClass().getMethod(methodName, new Class[] { String.class });
if(method!=null){
method.invoke(t, val);
}
} catch (Exception e) {
}
}
} catch (Exception e) {
e.printStackTrace();
return t;
}
return t;
}
public static String setMethodName(String fieldName){
StringBuffer methodName = new StringBuffer("set");
fieldName = fieldName.toLowerCase();
if(fieldName.indexOf("_") == 0){
methodName.append(fieldName);
}else{
methodName.append(toUpperCaseFirstOne(fieldName));
}
return methodName.toString();
}
//首字母转大写
public static String toUpperCaseFirstOne(String s)
{
if(Character.isUpperCase(s.charAt(0)))
return s;
else
return (new StringBuilder()).append(Character.toUpperCase(s.charAt(0))).append(s.substring(1)).toString();
}
}
相关文章推荐
- java 程序加载过程---3--类中申明同时申明类的静态对象 创建类的实例 访问类的静态变量 调用类的静态方法 使用反射方法 初始化类的子类对象 直接使用java.exe 调用某个类
- Java反射使用实例(http实体类转换)
- 使用反射创建Bean、Spring中是如何根据类名配置创建Bean实例、Java提供了Class类获取类别的字段和方法,包括构造方法
- Java反射学习总结四(动态代理使用实例和内部原理解析)
- Java反射及使用实例
- 使用java反射根据参数返回类的实例
- java学习---使用反射创建类的实例
- Java反射学习总结四(动态代理使用实例和内部原理解析)
- java使用反射实例
- java反射和自定义注解的使用实例
- Java反射API使用实例
- 使用反射创建Bean、Spring中是如何根据类名配置创建Bean实例、Java提供了Class类获取类别的字段和方法,包括构造方法
- 使用java反射中的getMethod,invoke方法调用对象方法的实例
- JAVA反射使用实例和class.getResource()得到URL中含有中文和空格乱码问题
- Java使用new和反射实例化内部类对象
- c# 反射使用实例
- Java 反射经典实例
- 反射使用的简单实例
- 使用java反射操作类的构造函数,成员变量和成员方法
- [转载]使用反射技术动态创建类对象(实例代码)