Lombok @Data使用的坑

发布时间:2024年01月11日

前言

? 在开发过程中,Lombok为我们提供了非常便捷的开发。使用注解,就能帮助我们生成get set 方法,使代码看起来更加优雅。但是@Data注解在有些情况下会有坑, 使用过程中慎用。

坑在什么地方

@Data
public class Person1 {
    private String idCard;
    private String sex;
}

@Data
@AllArgsConstructor
public class Student extends Person1 {
    private String school;
}

上面是两个常见的类,Student继承Person1.我们看下Student生成的class文件

//equals()方法
public boolean equals(Object o) {
        if (o == this) {
            return true;
        } else if (!(o instanceof Student)) {
            return false;
        } else {
            Student other = (Student)o;
            if (!other.canEqual(this)) {
                return false;
            } else {
                Object this$school = this.getSchool();
                Object other$school = other.getSchool();
                if (this$school == null) {
                    if (other$school != null) {
                        return false;
                    }
                } else if (!this$school.equals(other$school)) {
                    return false;
                }

                return true;
            }
        }
    }
    //hashCode 方法
   public int hashCode() {
        int PRIME = true;
        int result = 1;
        Object $school = this.getSchool();
        int result = result * 59 + ($school == null ? 43 : $school.hashCode());
        return result;
    }   

通过观察发现Student类重写了equals和hashCode方法。但是重写的这些方法里面只有本来的字段信息,没有父类的字段信息。

测试类

public class DateTest {
    public static void main(String[] args) {
        Student student1 = new Student("2");
        student1.setIdCard("2212");
        student1.setSex("1");
        Student student2 = new Student("2");
        student2.setIdCard("3333");
        student2.setSex("2");
        System.out.println(student1 == student2);
        System.out.println(student1.equals(student2));
        Map<Student,String> dataTestStringMap = new HashMap<>();
        dataTestStringMap.put(student1,student2.getSchool());
        dataTestStringMap.put(student2,student2.getSchool());
        System.out.println(dataTestStringMap.size());

        System.out.println(student1.hashCode());
        System.out.println(student2.hashCode());
    }
}

执行结果

false
true
1
109
109

你会发现 student1 和 student2 是两个对象,但是他们的hashCode 是相同的,并且equals方法结果是true。当我们使用hashCode和equals方法的时候,就会出现问题。

解决方案

方案一: 在student类上加上@EqualsAndHashCode(callSuper = true) 注解,重写父类的hashCode()和equals()

方案二: 按需加setter和getter

@Setter
@Getter
@AllArgsConstructor
public class Student extends Person1 {

    private String school;
}

结果我这里就不进行验证了,读者感兴趣的,请自行验证。

Lombok 对 @Data注解的解释

文档链接: https://projectlombok.org/features/Data

有兴趣的可以,阅读一下。

总结

? Lombok 是一个很优秀的Java库,简单的几个注解,可以干掉一大片的模版代码。当我们使用的时候,要知其然,也要知其所以然,这样才能避免不必要的坑。

文章来源:https://blog.csdn.net/weixin_50087960/article/details/135523249
本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。