我对OnetoOne和ManyToOne(不是OneToMany)的区别感到困惑.

让我们假设我们有一个Person类和一个Department类.当我们说多个Person可以属于一个Department时,我们假设一个ManyToOne关系,并在Person类中添加一个DeptID列.这对我来说是有意义的,并如所说的那样奏效.

然而,如果我们说Person和Department是一对一的关系,这意味着一个人只有一个部门,一个部门只有一个人.然而,这就是问题所在.JPA仍然允许两个Person对象共享同一个部门.

Person Class:

@Entity
@Table
public class Person {
    @Id
    @GeneratedValue(strategy= GenerationType.IDENTITY)
    int id;
    @Column
    int age;
    @Column(length = 20)
    String name;

    @Column(length = 20, nullable = true)
    String cnic;

    @Column(nullable = true)
    boolean married;

    @OneToOne
    Department dep;
}

Department Class:

@Entity
public class Department {
    @Id
    int Id;
    @Column
    String name;
}

Making two Persons with same Department:

public void testOTO() {
        System.out.println("Testing OTO");
        Department dep = new Department(202, "CS");
        depdb.saveAndFlush(dep);

        Person p1 = new Person();
        Person p2 = new Person();
        p1.setDep(dep);
        p2.setDep(dep);

        db.saveAndFlush(p1);
        db.saveAndFlush(p2);
}

我想问,OnetoOne和ManyToOne之间的区别只是语义上的,还是我错过了什么?

推荐答案

JPA本身并不控制您的一对一关系是否真的是一对一关系.但您的数据库模式可以.只需向外键列添加唯一约束即可.

JPA不判断这一点的原因是,在应用程序端这样做会非常昂贵. JPA需要获得整个表的外键列上的锁,然后判断要插入的值是否不在那里.

另一方面,数据库约束就是这方面的模式.虽然它们仍然需要锁定,但它们只锁定索引并自动执行.

我不确定流行的JPA实现在生成模式时是否会生成唯一约束.如果它们没有,这可能是因为它会与某些场景发生冲突,在这些场景中,短时间内存在两个相同的值.如果在创建唯一约束后遇到此类问题,则可能需要判断是否为your database supports deferred constraints.

Java相关问答推荐

将@ManyToOne JPA Composite Key用作Id保存实体添加额外参数

Java 8 RDX-如何设置单个选项卡标题文本的 colored颜色

如何配置ActiveMQ Artemis以使用AMQP 1.0和其他协议与Java

无法在WebSocket onMessage中捕获错误

Spring Boot@Cachebale批注未按预期工作

是否在允许数组元素为空时阻止 idea 为空性警告?

Jakarta CDI强制bean构造/注册遗留事件侦听器

对于亚洲/香港,使用ResolverStyle.STRICT的LocalDate.parse返回意外结果

基于接口的投影、原生查询和枚举

GetChildren().emoveAll()不会删除 node

Domino Designer 14中的保存代理添加了重影库

Java泛型类方法的静态返回类型是否被类型擦除?

是否为计划任务补偿系统睡眠?

Instancio未在日志(log)中显示测试失败消息

如何在太阳系模拟器中添加月球?

一对多关系和ID生成

使用SWIG将C++自定义单元类型转换为基本Java类型

带有可选部分的Java DateTimeForMatter

如何在不作为类出现的表上执行原生查询?

无法在IntStream上应用Collectors.groupingBy