Java比较两个对象是否相同并获得不同的字段

在使用数据库以及做详细的权限控制的时候,遇到要比较两个对象的情况,获得两个对象是否相同以及有那些字段被修改了,以判断用户是否有权限修改对象。apache commons提供的只有collections的对比,因此,本文利用jackson将对象序列化为map,通过对两个map的比较确定对象是否相等

访问我的个人网站获取更多文章


在撰写本文的时候,发现之前的方法麻烦了,研究了java map和list的equals方法,发现使用jackson序列化得到的map直接比较就好了!!


package org.uvlab.cloud.service.worktask.common;

import com.fasterxml.jackson.core.type.TypeReference;
import com.fasterxml.jackson.databind.ObjectMapper;
import java.util.HashMap;
import java.util.Map;
import java.util.Objects;

/**
 * Created by ysjiang on 2017/10/10.
 *Compare two object using defined fileds
 */
public class CompareUtils {

    private static final ObjectMapper mapper=new ObjectMapper();

    /**
     * Compare two object and return modified fields
     * @param source source object
     * @param target target object
     * @return the modified fields and value after modify
     */
    public static Map getModifyContent(Object source, Object target) {
        Map modifies=new HashMap<>();
         /*
          process null problem, if all null means equal
          if only source is null means all modified
          if only target is null means nothing changed
         */
        if(null == source || null == target) {
            if(null==source&&null==target) return modifies;
            else if(null == target) return modifies;
            else {return mapper.convertValue(target, new TypeReference>(){});}
        }
        // source and target must be same class type
        if(!Objects.equals(source.getClass().getName(), target.getClass().getName())){
            throw new ClassCastException("source and target are not same class type");
        }
        Map sourceMap= mapper.convertValue(source, new TypeReference>(){});
        Map targetMap = mapper.convertValue(target, new TypeReference>(){});
        sourceMap.forEach((k,v)->{
            Object targetValue=targetMap.get(k);
            if (!Objects.equals(v,targetValue)){modifies.put(k,targetValue);}
        });
        return modifies;
    }

    /**
     * Compare two object and return modified fields which contain in comparedProperties
     * @param source ource object
     * @param target target object
     * @param comparedProperties the fields need to be compare
     * @return the modified fields and value after modify
     */
    public static Map getModifyContent(Object source, Object target,Map comparedProperties) {
        Map modifies=new HashMap<>();
        if(null == source || null == target) {
            if(null==source&&null==target) return modifies;
            else if(null == target) return modifies;
            else {return mapper.convertValue(target, new TypeReference>(){});}
        }
        if(!Objects.equals(source.getClass().getName(), target.getClass().getName())){
            throw new ClassCastException("source and target are not same class type");
        }
        Map sourceMap= mapper.convertValue(source, new TypeReference>(){});
        Map targetMap = mapper.convertValue(target, new TypeReference>(){});
        sourceMap.forEach((k,v)->{
            if(comparedProperties!=null&&!comparedProperties.containsKey(k)){
                return;
            }
            Object targetValue=targetMap.get(k);
            if (!Objects.equals(v,targetValue)){modifies.put(k,targetValue);}
        });
        return modifies;
    }

    /**
     * Compare two object and return if equal
     * @param source source object
     * @param target target object
     * @return true-equal
     */
    public static boolean isEuqal(Object source, Object target) {
        if(null == source || null == target) {
            return false;
        }
        if(!Objects.equals(source.getClass().getName(), target.getClass().getName())){
            return false;
        }
        Map sourceMap= mapper.convertValue(source, new TypeReference>(){});
        Map targetMap = mapper.convertValue(target, new TypeReference>(){});
        return Objects.equals(sourceMap,targetMap);
    }

    /**
     * Compare two object and return if equal
     * @param source source object
     * @param target target object
     * @param comparedProperties only compare fields in this map
     * @return  rue-equal
     */
    public static boolean isEuqal(Object source, Object target,Map comparedProperties) {
        if(null == source || null == target) {
            return null == source && null == target;
        }
        if(!Objects.equals(source.getClass().getName(), target.getClass().getName())){
            return false;
        }
        Map sourceMap= mapper.convertValue(source, new TypeReference>(){});
        Map targetMap = mapper.convertValue(target, new TypeReference>(){});
        for(String k:sourceMap.keySet()){
            if(comparedProperties!=null&&!comparedProperties.containsKey(k)){
                continue;
            }
            Object v=sourceMap.get(k);
            Object targetValue=targetMap.get(k);
            if(!Objects.equals(v,targetValue)){return false;}
        }
        return true;
    }
}

Java比较两个对象是否相同并获得不同的字段_第1张图片

你可能感兴趣的:(java)