前言

org.springframework.beans.BeanUtils,它提供了对java反射和自省API的包装。它里面还有很多工具类,这里我们介绍一下copyProperties。

我们如果有两个具有很多相同属性的JavaBean对象a和b,想把a中的属性赋值到b,比如接口中将接收到的前端请求参数封装为XxxReqVo,我们想把他转化为XxxQuery对象作为数据库的查询条件,XxxReqVo封装了前端传给我们的参数,接口中我们new了一个XxxQuery对象,属性全是空的,需要把XxxReqVo的相关字段赋值给XxxQuery,最笨的方法就是一个个set

xxQuery.setA(xxReqVO.getA());

如果有几十个需要赋值的的字段呢?那就很头疼了,该工具方法则帮我们大大简化这一步骤

案例

@Data
public class User {private String id;private String name;private String age;private String account;private String password;
}
@Data
public class Person {private String id;private String name;private String age;private String sex;
}
public class Test {public static void main(String[] args) {User user = new User();user.setId("1");user.setAge("2");user.setName("wzh");user.setAccount("wangzh");user.setPassword("1111");Person person = new Person();BeanUtils.copyProperties(user,person);}
}

结果

Person(id=1, name=wzh, age=2, sex=null)

通过上述测试我们就可以总结出相关结论,基本用法为

BeanUtils.copyProperties("转换前的类a", "转换后的类b");

作用:相当于把a的属性赋值给b;

前提:

  • 把a中和b中相同属性名的属性值赋给b;a中和b不相同属性名的属性不会赋值给b
  • a和b类中的属性必须对应setter/getter方法,没有setter/getter则无法完成赋值

官网文档

英文版

Copy the property values of the given source bean into the given target bean.
Note: The source and target classes do not have to match or even be derived from each other, as long as the properties match.
Any bean properties that the source bean exposes but the target bean does not will silently be ignored.As of Spring Framework 5.3, this method honors generic type information when matching properties in the source and target objects.

中文版

将给定源bean的属性值复制到给定的目标bean中。注意:只要属性匹配,源类和目标类不必相互匹配,甚至不必相互派生。源bean公开而目标bean没有公开的任何bean属性都将被静默地忽略。从Spring Framework 5.3开始,当匹配源对象和目标对象中的属性时,该方法将尊重泛型类型信息

源码分析

/**
Params:
source – the source bean #赋值的源对象source
target – the target bean #赋值的目标对象target
editable – the class (or interface) to restrict property setting to  #将属性设置限制为的类(或接口)
ignoreProperties – array of property names to ignore  #要忽略的属性名数组
Throws:
BeansException – if the copying failed*/
private static void copyProperties(Object source, Object target, @Nullable Class<?> editable,@Nullable String... ignoreProperties) throws BeansException {//合法性判断Assert.notNull(source, "Source must not be null");Assert.notNull(target, "Target must not be null");//获取赋值的目标对象target的class对象Class<?> actualEditable = target.getClass();if (editable != null) {if (!editable.isInstance(target)) {throw new IllegalArgumentException("Target class [" + target.getClass().getName() +"] not assignable to Editable class [" + editable.getName() + "]");}actualEditable = editable;}/*** 该方法检索给定类(赋值的目标对象target的类型)的JavaBeans propertydescriptor* 返回结果是propertydescriptor数组格式* PropertyDescriptor类:描述了Java Bean通过一对访问器(getter/setter)方法导出的一个属性。* 这里target对象有4个属性,所以targetPds数组长度为4*/PropertyDescriptor[] targetPds = getPropertyDescriptors(actualEditable);List<String> ignoreList = (ignoreProperties != null ? Arrays.asList(ignoreProperties) : null);for (PropertyDescriptor targetPd : targetPds) {Method writeMethod = targetPd.getWriteMethod();//获取target对象的setter方法(Method类型),例如此时遍历到id这个属性if (writeMethod != null && (ignoreList == null || !ignoreList.contains(targetPd.getName()))) {//获取source中和该target属性的写入器(setId)同名的的写入器PropertyDescriptor sourcePd = getPropertyDescriptor(source.getClass(), targetPd.getName());if (sourcePd != null) { //获取到 => source中有和该target属性的写入器(setId)同名的的写入器Method readMethod = sourcePd.getReadMethod();//获取source的getId方法if (readMethod != null) {  //获取成功ResolvableType sourceResolvableType = ResolvableType.forMethodReturnType(readMethod);ResolvableType targetResolvableType = ResolvableType.forMethodParameter(writeMethod, 0);// Ignore generic types in assignable check if either ResolvableType has unresolvable generics.boolean isAssignable =(sourceResolvableType.hasUnresolvableGenerics() || targetResolvableType.hasUnresolvableGenerics() ?ClassUtils.isAssignable(writeMethod.getParameterTypes()[0], readMethod.getReturnType()) :targetResolvableType.isAssignableFrom(sourceResolvableType));if (isAssignable) {try {if (!Modifier.isPublic(readMethod.getDeclaringClass().getModifiers())) {readMethod.setAccessible(true);}//利用反射读取source源对象中的属性(id)值赋值给value,等价于source.getId();Object value = readMethod.invoke(source);if (!Modifier.isPublic(writeMethod.getDeclaringClass().getModifiers())) {writeMethod.setAccessible(true);}//设置对象target的相关属性值为valuewriteMethod.invoke(target, value);}catch (Throwable ex) {throw new FatalBeanException("Could not copy property '" + targetPd.getName() + "' from source to target", ex);}}}}}}}

核心代码

/**
* 检索给定类的JavaBeans propertydescriptor。参数:clazz -为其检索propertydescriptor的类返回:给定类的propertydescriptor数组抛出:BeansException -如果PropertyDescriptor查找失败
*/
PropertyDescriptor[] targetPds = getPropertyDescriptors(actualEditable);

BeanUtils.copyProperties的用法相关推荐

  1. (转载)BeanUtils.copyProperties() 用法

    BeanUtils.copyProperties() 用法 标签: hibernateuserjdbc数据库strutsjava 2009-10-17 23:04 35498人阅读 评论(6) 收藏  ...

  2. BeanUtils.copyProperties与PropertyUtils.copyProperties用法及区别

    转自:http://www.cnblogs.com/fayf/articles/1272982.html 一.简介:BeanUtils提供对Java反射和自省API的包装.其主要目的是利用反射机制对J ...

  3. BeanUtils.copyProperties() 用法

    转载自 https://blog.csdn.net/jdjdndhj/article/details/62056137 第一步: BeanUtils.copyProperties()与Property ...

  4. 关于BeanUtils.copyProperties的用法和优缺点

    一.简介:  BeanUtils提供对Java反射和自省API的包装.其主要目的是利用反射机制对JavaBean的属性进行处理.我们知道,一个JavaBean通常包含了大量的属性,很多情况下,对Jav ...

  5. BeanUtils.copyProperties使用

    BeanUtils提供对Java反射和自省API的包装.其主要目的是利用反射机制对JavaBean的属性进行处理.我们知道,一个JavaBean通常包含了大量的属性,很多情况下,对JavaBean的处 ...

  6. 使用BeanUtils.copyProperties进行对象之间的属性赋值

    1.使用org.springframework.beans.BeanUtils.copyProperties方法进行对象之间属性的赋值,避免通过get.set方法一个一个属性的赋值 /*** 对象属性 ...

  7. BeanUtils.copyProperties VS PropertyUtils.copyProperties

    1. 通过反射将一个对象的值赋值个另外一个对象(前提是对象中属性的名字相同). 2. BeanUtils.copyProperties(obj1,obj2); 经常闹混不知道是谁给谁赋值,无意中先到& ...

  8. 小知识点BeanUtils.copyProperties

     通过BeanUtils.copyProperties可以时间拷贝对象中的值,下面的new String[]{"cid","agreeFlag"," ...

  9. java对象复制到另一个对象中_spring: beanutils.copyproperties将一个对象的数据塞入到另一个对象中(合并对象)...

    spring: beanutils.copyproperties将一个对象的数据塞入到另一个对象中(合并对象) 它的出现原因: BeanUtils提供对Java反射和自省API的包装.其主要目的是利用 ...

最新文章

  1. HJ107 二分法求求解立方根
  2. 详解PyTorch中的ModuleList和Sequential
  3. python函数(三)
  4. 我的2013年度总结
  5. Nacos-服务多级存储模型
  6. python基础入门大作业怎么做_【百度飞桨】零基础Python课程大作业
  7. html 弹出一个邮件连接,mailto scheme 高级用法, 显示带html样式的邮件文本
  8. linux7自动挂载怎么做,CentOS7 Virtual Box 开机自动挂载共享文件夹
  9. 在Tomcat 与weblogic 中的 日志(log4j) 配置系列二(weblogic 应用程序使用log4j)
  10. 技术系统优化还可以这样做?
  11. 算法导论笔记 第三十章 多项式与快速傅里叶变化
  12. xp也可以将U盘格为NTFS
  13. H264 SPS分析
  14. 关于getX()getY()就可以获取到位置,找不到方法问题
  15. 计算机开机只显示桌面不显示图标,电脑开机后只有桌面背景不显示图标怎么办...
  16. ddos应急处理_DDOS攻击应急响应预案
  17. 计算机二级考试用的什么Word,计算机二级考试内容大纲_计算机二级office考什么...
  18. “云脉文档管理”微信小程序提供高效的办公体验
  19. Android接收短信和发送短信
  20. 220216HTML学习日记

热门文章

  1. 世相科技:引领新媒体时代的潮水方向
  2. 电脑出现负片情况,底片效果怎么解决?(win10颜色滤镜功能)
  3. 在VMwareWorkstation的虚拟机上安装“行云管家”过程记录,未来可以测试了。
  4. 【期权、期货及其衍生产品】学习笔记1(期权、远期)
  5. Swift中由找不到removeAll(where:)方法引起的连锁反应(下)
  6. 利用Mavros控制无人机
  7. WinXW_android
  8. starccm+电池包热管理-新能源汽车电池包共轭传热仿真
  9. 一文直观理解编译型语言、解释型语言和脚本语言的区别
  10. 墨珩科技荣获“高新技术企业”认定