代码中有很多对象都用同样的属性名称,不一样的值,进行set值时,一堆重复代码,所以才产生了下面的想法:
通过反射和属性键值对调用一个通用的方法,实现对象的属性进行赋值,这样就可以避免很多重复代码了。
以下是我实现的三种方式:
方式一:
代码中通过方法set前缀和后缀匹配的方式获得需要调用的set方法。
public static <C> void setValueByFieldName(C c, Map<String, Object> fieldAndValues) throws Exception { List<Method> methods = Arrays.stream(c.getClass().getMethods()) .filter(m -> m.getName().startsWith("set") && fieldAndValues.containsKey(m.getName().substring(3, 4).toLowerCase() + m.getName().substring(4)) ).collect(Collectors.toList()); for (Method m : methods) { m.invoke(c, fieldAndValues.get(m.getName().substring(3, 4).toLowerCase() + m.getName().substring(4))); } }
方式二:
通过Field名称和key一致,调用Field.set方法
public static <C> void setValueByFieldName_(C c, Map<String, Object> fieldAndValues) throws Exception { List<Field> fields = Arrays.stream(c.getClass().getDeclaredFields()) .filter(f -> fieldAndValues.containsKey(f.getName())) .collect(Collectors.toList()); for (Field field : fields) { field.setAccessible(true); field.set(c, fieldAndValues.get(field.getName())); } }
通过Field名称一致的方式获得需要调用set方法的Field列表,然后调用其set方法进行赋值
方式三:
通过Class对象获得类的结构信息,然后获得所有属性列表,通过属性获得WriteMethod进行赋值。
public static <C> void setValueByFieldName__(C c, Map<String, Object> fieldAndValues) throws Exception { BeanInfo beanInfo = Introspector.getBeanInfo(c.getClass()); List<PropertyDescriptor> properties = Arrays.stream(beanInfo.getPropertyDescriptors()) .filter(f -> fieldAndValues.containsKey(f.getName())).collect(Collectors.toList()); for (PropertyDescriptor property : properties) { Method setMethod = property.getWriteMethod(); if (setMethod != null) { setMethod.invoke(c, fieldAndValues.get(property.getName())); } } }
说明:
c:是需要进行属性赋值的对象;
fieldAndValues:是需要赋值属性名称的键值对。
以上是我实现的三种方式,如有更好的方式,欢迎探讨提携……
活到老,豪横到老,我又发现更有效率的方式了!
双手托碗,领福利喽!
public static <C> void setValueByFieldName___(C c, Map<String, Object> fieldAndValues) throws Exception { for (String f : fieldAndValues.keySet()) { PropertyDescriptor propertyDescriptor = new PropertyDescriptor(f, c.getClass()); Method set; if (null != propertyDescriptor && null != (set = propertyDescriptor.getWriteMethod())) { set.invoke(c, fieldAndValues.get(f)); } } }
不用获取所有属性,只需要一针见血的干倒敌人就可以了……
来源:oschina
链接:https://my.oschina.net/kevin2kelly/blog/3216634