有没有办法知道两个bean之间哪些属性不同?

时间:2012-10-29 13:37:00

标签: java javabeans

我想以与Hibernate Envers类似的方式继续对我的bean进行更改(但我不能使用Envers,因为我没有连接到JDBC后端)。

所以,为此,我想知道,在给定bean类的两个实例之间,哪些属性具有不同的值。

更清楚的是,当给出bean A和B时,我想有一个方法...说... diff(A, B),它会输出一个列表(或地图)链接属性到他们的旧/新值。

这样的东西
<BeanClass> Collection<Field, Entry<Object, Object> diff(BeanClass a, BeanClass b)

在Java世界中是否有一个库可以做到这一点?

5 个答案:

答案 0 :(得分:3)

嗯,解决方案是使用java-object-diff,它提供了一个可访问的对象之间的差异树。结果,我们最终使用该库取得了巨大成功。

答案 1 :(得分:0)

你可以使用Reflection + Apache Commons BeanUtils。递归部分将是棘手的,如果你想做深度差异。

答案 2 :(得分:0)

编辑: 当然,有许多与反射有关的工作(由其他人写),这是你应该开始的地方。

顺便说一句,我刚刚找到了一个应该做你想要的项目,只需从存储库中检出主干:

https://code.google.com/p/beandiff/source/checkout

希望有所帮助


尝试查看Apache BeanComparator;

  

此比较器按指定的bean属性比较两个bean。它   也可以基于嵌套,索引,组合,比较bean   映射的bean属性。请参阅PropertyUtilsBean文档   所有属性名称的可能性。

compare(java.lang.Object o1, java.lang.Object o2)
          Compare two JavaBeans by their shared property.

答案 3 :(得分:0)

您可以使用EqulasBuilder class from Apache Commons

String[] Arr = new String[excludedFields.size()]; //Add fields you want to exclude in here

boolean result = EqualsBuilder.reflectionEquals(object2, object1,Arr);

if(!result){
    System.out.println("----- Failure:" + StringUtils.difference(ReflectionToStringBuilder.toStringExclude(object1,excludedFields),ReflectionToStringBuilder.toStringExclude(object2,excludedFields)));
    return false;
}

答案 4 :(得分:0)

类似的东西:

public <T> Map<Field, Entry<Object, Object>> diff(T a, T b){
    //... initialize the map
    for (Method m : a.getClass().getMethods()){
        if(m.getName().startsWith("get")){
            Object obj1 = m.invoke(a, null);
            Object obj2 = m.invoke(b, null);
            if(!obj1.equals(obj2)){
                //converts getName to name, for example
                String fieldName = m.getName()...; 
                map.put(a.getClass().getField(fieldName), new Entry(obj1, obj2));
            }
        }
    }
}

考虑您遵循Java Beans惯例。