有时一个实体的主键可能同时为多个,例如同样是之前使用的“
CustomerEO
”实体,需要通过
name
和
email
来查找指定实体,当且仅当
name
和
email
的值完全相同时,才认为是相同的实体对象。要配置这样的复合主键,步骤如以下所示。
(
1
)编写一个复合主键的类
CustomerPK
,代码如下。
import java.io.Serializable;
public class CustomerPK implements Serializable
{
public CustomerPK() {
}
public CustomerPK(String name, String email) {
this.name = name;
this.email = email;
}
private String email;
public String getEmail() {
return email;
}
public void setEmail(String email) {
this.email = email;
}
private String name;
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
@Override
public int hashCode() {
final int PRIME = 31;
int result = 1;
result = PRIME * result + ((email == null) ? 0 : email.hashCode());
result = PRIME * result + ((name == null) ? 0 : name.hashCode());
return result;
}
@Override
public boolean equals(Object obj) {
if (this == obj)
return true;
if (obj == null)
return false;
if (getClass() != obj.getClass())
return false;
final CustomerPK other = (CustomerPK) obj;
if (email == null) {
if (other.email != null)
return false;
} else if (!email.equals(other.email))
return false;
if (name == null) {
if (other.name != null)
return false;
} else if (!name.equals(other.name))
return false;
return true;
}
}
作为符合主键类,要满足以下几点要求。
l
必须实现
Serializable
接口。
l
必须有默认的
public
无参数的构造方法。
l
必须覆盖
equals
和
hashCode
方法。
equals
方法用于判断两个对象是否相同,
EntityManger
通过
find
方法来查找
Entity
时,是根据
equals
的返回值来判断的。本例中,只有对象的
name
和
email
值完全相同时或同一个对象时则返回
true
,否则返回
false
。
hashCode
方法返回当前对象的哈希码,生成的
hashCode
相同的概率越小越好,算法可以进行优化。
(
2
)通过
@IdClass
注释在实体中标注复合主键,实体代码如下。
@Entity
@Table(name = "customer")
@IdClass(CustomerPK.class)
public class CustomerEO implements java.io.Serializable {
private Integer id;
public Integer getId() {
return this.id;
}
public void setId(Integer id) {
this.id = id;
}
private String name;
@Id
public String getName() {
return this.name;
}
public void setName(String name) {
this.name = name;
}
private String email;
@Id
public String getEmail() {
return email;
}
public void setEmail(String email) {
this.email = email;
}
}
标注复合主键时需要注意以下几个问题。
l
@IdClass
标注用于标注实体所使用主键规则的类。它的定义如下所示。
@Target({TYPE}) @Retention(RUNTIME)
public @interface IdClass {
Class value();
}
属性
Class
表示符合主键所使用的类,本例中使用
CustomerPK
这个复合主键类。
l
在实体中同时标注主键的属性。本例中在
email
和
name
的
getter
方法前标注
@Id
,表示符合主键使用这两个属性。
(
3
)这样定义实体的复合主键后,通过以下代码便可以获得指定的实体对象:
CustomerPK cpk = new CustomerPK("Janet","janetvsfei@yahoo.com.cn");
CustomerEO instance = entityManager.find(CustomerEO.class, cpk);
提示:符合主键的值一般要通过程序设置,而不是按照某一个规则自动生成的。
分享到:
相关推荐
使用@IdClass创建联合主键,并实现外部关联
联合主键用Hibernate注解映射方式主要有三种: 第一、将联合主键的字段单独放在一个类...最后在主类中(该类包含联合主键类中的字段)将联合主键字段都注解为@Id,并在该类上方将上这样的注解:@IdClass(联合主键类.class)
linux驱动开发——怎么写alsa驱动官方文档
023 复合主键 关联映射 024 其它 关联映射 025 hibernate 悲观锁、乐观锁 026 hibernate 操作树形结构 027 hibernate 查询语言(HQL) 028 hibernate 缓存(性能优化策略) 029 hibernate 抓取策略
o @IdClass o @Inheritance • J o @JoinColumn o @JoinColumns o @JoinTable • L o @Lob • M o @ManyToMany o @ManyToOne o @MapKey o @MappedSuperclass • N o @NamedNativeQueries o @NamedNativeQuery o @...
• 将类注解为 @IdClass,并将该实体中所有主键的属性都注解为 @Id @Entity @IdClass(FootballerPk.class) public class Footballer { //part of the id key @Id public String getFirstname() { return ...
目前IE浏览器仍旧是大型web系统首选的浏览器,有很大的一个原因就是IE浏览器支持ActiveX控件,可以很简单的和本地设备进行通讯和调用一些C/C++的一些程序完成沙盒之外的一些功能。 ShowActiveXIF是个非常简单,容易...
Cabinet File Utility Classes小巧的文件工具类(7KB)
from dataclasses import dataclass @ dataclass class InventoryItem : name : str unit_price : float quantity_on_hand : int 然后我们可以使用JSONSerializer将其序列化到/从JSON反序列化。 >>> from data...
主要介绍了SpringBoot2.0整合WebSocket代码实例,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友可以参考下
一、创建序列 1.1、直接在PLSQL中设置 1.2、命令创建 create sequence seq_users ##创建序列seq_users increment by 1 ## 步长,每次加1 start with 1 ##从1开始 minvalue 1 ##最小值 maxvalue 9999999 ##最大值 ...
dataclass - dataclass_generator - 用于@DataClass注释 DataClass 生成器使用以下方法为您的数据类生成基类: 等于(运算符 ==) hashCode 字符串 复制与 入门 0. 将依赖添加到 pubspec.yaml dependencies :...
@Id public Integer getId() { return id; } public void setId(Integer id) { this.id = id; } @OneToOne @PrimaryKeyJoinColumn public Heart getHeart() { return heart; } public void setHeart...
它是使用新的 @dataclass 装饰器创建的,如下所示: from dataclasses import dataclass @dataclass class DataClassCard: rank: str suit: str 此代码以及本教程中的所有其他示例仅适用于 Python 3.7 及更高版本...
@ dataclass class Point2D : x : int y : int 遗产 如文档中所述,在派生类__dict__中创建了,因为基类没有__slots__。 插槽是从所有定义的属性创建的(由dataclasses.fields()函数返回)。 @ dataclass class...
from class_resolver import Resolver from dataclasses import dataclass class Base : pass @ dataclass class A ( Base ): name : str @ dataclass class B ( Base ): name : str # Index resolver = Resolver ...
将您的类别标记为@Poko class而不是data class : @Poko class MyData ( val int : Int , val requiredString : String , val optionalString : String? ) 并享受可读的toString和有效的equals和hashCode的好处...
Hash_ID.class
lua 面向对象