Java反射通过Getter方法获取对象VO的属性值过程解析

 更新时间:2020年02月12日 13:00:30   作者:Nick Huang  
这篇文章主要介绍了Java反射通过Getter方法获取对象VO的属性值过程解析,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友可以参考下

这篇文章主要介绍了Java反射通过Getter方法获取对象VO的属性值过程解析,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友可以参考下

有时候,需要动态获取对象的属性值。

比如,给你一个List,要你遍历这个List的对象的属性,而这个List里的对象并不固定。比如,这次User,下次可能是Company。

e.g. 这次我需要做一个Excel导出的工具类,导出的批量数据是以List类型传入的,List里的对象自然每次都不同,这取决于需要导出什么信息。

为了使用方便,将对象的属性名与属性值存于Map当中,使用时就可以直接遍历Map了。

此次的思路是通过反射和Getter方法取得值,然后记录在一个Map当中。

Kick start...

将对象的属性名与属性值存于Map当中,以key,value的形式存在,而value并不希望以单一类型(如String)存在(因为涉及多种类型),所以用一个FieldEntity的自定义类(此类包含属性名,属性值,属性值类型 等属性)

FieldEntity

package com.nicchagil.util.fields;


import java.lang.reflect.Field;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.util.HashMap;
import java.util.Map;

public class FieldsCollector {

  public static Map<String, FieldEntity> getFileds(Object object) 
      throws SecurityException, IllegalArgumentException, NoSuchMethodException, 
      IllegalAccessException, InvocationTargetException {
    Class clazz = object.getClass();
    Field[] fields = clazz.getDeclaredFields();
    Map<String, FieldEntity> map = new HashMap<String, FieldEntity> ();
    
    for (int i = 0; i < fields.length; i++) {
      
      Object resultObject = invokeMethod(object, fields[i].getName(), null);
      map.put(fields[i].getName(), new FieldEntity(fields[i].getName(), resultObject, fields[i].getType()));
    }
    
    return map;
  }

  public static Object invokeMethod(Object owner, String fieldname,
      Object[] args) throws SecurityException, NoSuchMethodException, 
      IllegalArgumentException, IllegalAccessException, InvocationTargetException {
    Class ownerClass = owner.getClass();
    
    Method method = null;
    method = ownerClass.getMethod(GetterUtil.toGetter(fieldname));

    Object object = null;
    object = method.invoke(owner);

    return object;
  }

}

主类,通过这个类的静态方法获取结果Map

FieldsCollector

package com.nicchagil.util.fields;


import java.lang.reflect.Field;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.util.HashMap;
import java.util.Map;

public class FieldsCollector {

  public static Map<String, FieldEntity> getFileds(Object object) 
      throws SecurityException, IllegalArgumentException, NoSuchMethodException, 
      IllegalAccessException, InvocationTargetException {
    Class clazz = object.getClass();
    Field[] fields = clazz.getDeclaredFields();
    Map<String, FieldEntity> map = new HashMap<String, FieldEntity> ();
    
    for (int i = 0; i < fields.length; i++) {
      
      Object resultObject = invokeMethod(object, fields[i].getName(), null);
      map.put(fields[i].getName(), new FieldEntity(fields[i].getName(), resultObject, fields[i].getType()));
    }
    
    return map;
  }

  public static Object invokeMethod(Object owner, String fieldname,
      Object[] args) throws SecurityException, NoSuchMethodException, 
      IllegalArgumentException, IllegalAccessException, InvocationTargetException {
    Class ownerClass = owner.getClass();
    
    Method method = null;
    method = ownerClass.getMethod(GetterUtil.toGetter(fieldname));

    Object object = null;
    object = method.invoke(owner);

    return object;
  }

}

为了代码清楚些,将一些工具方法独立一下,如field name到getter name的转换方法

GetterUtil

package com.nicchagil.util.fields;

public class GetterUtil {
  
  /**
   * Get getter method name by field name
   * @param fieldname
   * @return
   */
  public static String toGetter(String fieldname) {
    
    if (fieldname == null || fieldname.length() == 0) {
      return null;
    }
    
    /* If the second char is upper, make 'get' + field name as getter name. For example, eBlog -> geteBlog */
    if (fieldname.length() > 2) {
      String second = fieldname.substring(1, 2);
      if (second.equals(second.toUpperCase())) {
        return new StringBuffer("get").append(fieldname).toString();
      }
    }
    
    /* Common situation */
    fieldname = new StringBuffer("get").append(fieldname.substring(0, 1).toUpperCase())
        .append(fieldname.substring(1)).toString();
    
    return fieldname;
  }

}

大功告成!!!

现在,写个VO作为模拟数据

User

import java.util.Date;

public class User {

  private String username;
  private String password;
  private String eBlog;
  private Date registrationDate;
  
  public String getUsername() {
    return username;
  }

  public void setUsername(String username) {
    this.username = username;
  }

  public String getPassword() {
    return password;
  }

  public void setPassword(String password) {
    this.password = password;
  }

  public String geteBlog() {
    return eBlog;
  }

  public void seteBlog(String eBlog) {
    this.eBlog = eBlog;
  }

  public Date getRegistrationDate() {
    return registrationDate;
  }

  public void setRegistrationDate(Date registrationDate) {
    this.registrationDate = registrationDate;
  }

}

最后,测试类,此类将直接调用FieldsCollector~~

Call

import java.util.Date;
import java.util.Map;

import com.nicchagil.util.fields.FieldEntity;
import com.nicchagil.util.fields.FieldsCollector;



public class Call {
  
  public static void main(String[] args) throws Exception {
    
    User user = new User();
    user.setUsername("user109");
    user.setPassword("pwd109");
    user.seteBlog("http://www.cnblogs.com/nick-huang/");
    user.setRegistrationDate(new Date());
    
    Map<String, FieldEntity> map = FieldsCollector.getFileds(user);
    System.out.println(map);
    
  }

}

Oh year, 成功了~~~

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持脚本之家。

您可能感兴趣的文章:

相关文章

  • SpringBoot如何设置404、500返回统一格式json

    SpringBoot如何设置404、500返回统一格式json

    这篇文章主要介绍了SpringBoot如何设置404、500返回统一格式json问题,具有很好的参考价值,希望对大家有所帮助,如有错误或未考虑完全的地方,望不吝赐教
    2024-08-08
  • spring如何使用命名空间p简化bean的配置

    spring如何使用命名空间p简化bean的配置

    这篇文章主要介绍了spring如何使用命名空间p简化bean的配置,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友可以参考下
    2020-01-01
  • 详解java中&和&&的区别

    详解java中&和&&的区别

    这篇文章主要介绍了java中&和&&的区别,在java中比较常见的运算符:&&(短路与)、&、||(短路或)、|,需要的朋友可以参考下
    2015-07-07
  • SpringBoot整合activemq的案例代码

    SpringBoot整合activemq的案例代码

    ActiveMQ是消息队列技术,为解决高并发问题而生,本文通过案例代码给大家介绍pringBoot整合activemq的详细过程,感兴趣的朋友跟随小编一起看看吧
    2022-02-02
  • IDEA利用自带Axis工具和wsdl文件反向生成服务端客户端代码图文详解

    IDEA利用自带Axis工具和wsdl文件反向生成服务端客户端代码图文详解

    这篇文章主要介绍了IDEA利用自带Axis工具和wsdl文件反向生成服务端客户端代码详细流程,在这里小编使用的是idea2021.1最新开发工具,本文通过图文并茂的形式给大家介绍的非常详细,需要的朋友可以参考下
    2021-05-05
  • SpringBoot整合rockerMQ消息队列详解

    SpringBoot整合rockerMQ消息队列详解

    今天和大家一起深入生产级别消息中间件 - RocketMQ 的内核实现,来看看真正落地能支撑万亿级消息容量、低延迟的消息队列到底是如何设计的。我会先介绍整体的架构设计,然后再深入各核心模块的详细设计、核心流程的剖析
    2022-07-07
  • 使用IDEA创建SpringBoot项目

    使用IDEA创建SpringBoot项目

    本文详细介绍了使用SpringBoot创建项目,包含配置、启动、开发环境配置等,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下面随着小编来一起学习学习吧
    2024-12-12
  • Idea打不了断点如何解决

    Idea打不了断点如何解决

    这篇文章主要介绍了Idea打不了断点如何解决的问题,具有很好的参考价值,希望对大家有所帮助。如有错误或未考虑完全的地方,望不吝赐教
    2023-03-03
  • java实现的日期时间转换工具类完整示例

    java实现的日期时间转换工具类完整示例

    这篇文章主要介绍了java实现的日期时间转换工具类,结合完整实例形式分析了java针对日期时间常见的转换、计算、格式化等相关操作与封装技巧,需要的朋友可以参考下
    2019-10-10
  • Hadoop源码分析六启动文件namenode原理详解

    Hadoop源码分析六启动文件namenode原理详解

    本篇是Hadoop源码分析系列文章第六篇,主要介绍Hadoop中的启动文件namenode,后续本系列文章会持续更新,有需要的朋友可以借鉴参考下
    2021-09-09

最新评论