使用反射将Map的key-value映射成对象

 直接进入主题吧

首先是造对象,创建了一个user对象,包含了user2对象

@Data
public class User {
    private String name;
    private Integer age;
    private double weight;
    private String gender;
    private User2 user2;

    public User() {

    }
}
@Data
@AllArgsConstructor
@NoArgsConstructor
public class User2 {
    private String name;
    private Integer age;

}

 map给了4个key,其中class在user属性中不存在;

user对象中gender在map中也不存在。

把user和map丢进reflex方法中,接下来主要看reflex的逻辑。

public static void main(String[] args) {

        HashMap map = new HashMap<>();
        map.put("name", "Jack");
        map.put("age", 18);
        map.put("weight", 175.5);
        map.put("class", "一班");
        User user = new User();
        reflex(user, map);
        System.out.println("user = " + user);
    }
  1. 先获取Class对象,利用反射获取所有字段包括私有的,遍历字段
  2. 判断字段的类型,主要分为:基本类型、基本类型的包装类、String、List、Map、自定义对象
  3. 因可能出现字段名相同,但类型不一致的情况,这种情况不能赋值。
  4. 当type为基本数据类型时,map中的value为对应的类或包装类直接set
  5. 当type的类型在list中,赋值前需要判断与value类型是否一致
  6. 最后,当type为自定义类型时,这个时候通过获取构造器,得到对应对象,把对应对象进行递归处理
  7. 重点还有一个,因user和user2中都有name和age属性,这个时候默认是都赋值的,且值相同
//反射
    public static  void reflex(T obj, Map map) {
        List list = Lists.newArrayList(Boolean.class, Character.class, Byte.class, Short.class, Integer.class, Long.class, Float.class, Double.class, String.class, Collection.class, List.class, Map.class);
        try {
            Class cla = obj.getClass();
            Field[] fields = cla.getDeclaredFields();
            for (Field field : fields) {
                Class type = field.getType();
                field.setAccessible(true);
                System.out.println("filedType = " + type);
                //判断是否为基本类型
                if (type.isPrimitive()) {
                    String name = field.getName();
                    System.out.println("filedName = " + name);
                    Object value = map.get(name);
                    if (value != null && type.toString().equals(value.getClass().getSimpleName().toLowerCase())) {
                        //类中可能会包含对象或父类,可能会出现重复属性,只要字段名相同,默认都赋值
                        field.set(obj, value);
                    }
                } else if (list.contains(type)) {
                    String name = field.getName();
                    System.out.println("filedName = " + name);
                    Object value = map.get(name);
                    if (value != null && value.getClass() == type) {
                        //类中可能会包含对象或父类,可能会出现重复属性,只要字段名相同,默认都赋值
                        field.set(obj, value);
                    }
                } else {
                    Constructor declaredConstructor1 = type.getDeclaredConstructor();
                    declaredConstructor1.setAccessible(true);
                    Object obj1 = declaredConstructor1.newInstance();
                    reflex(obj1, map);
                    field.set(obj, obj1);
                }
            }
        } catch (Exception e) {
            e.printStackTrace();
        }
    }

第一次写,有不对的地方欢迎评论区交流,互相学习。

你可能感兴趣的:(java,spring)