hibernate_ID生成策略
increment:主键按数值顺序递增。此方式的实现机制为在当前应用实例中维持一个变量,以保存着当前的最大值,之后每次需要生成主键的时候将此值加1作为主键。这种方式可能产生的问题是:如果当前有多个实例访问同一个数据库,那么由于各个实例各自维护主键状态,不同实例可能生成同样的主键,从而造成主键重复异常。因此,如果同一数据库有多个实例访问,此方式必须避免使用;
1)identity:
采用数据库提供的主键生成机制。如DB2、SQL Server、MySQL中的主键生成机制。
2)sequence
采用数据库提供的sequence 机制生成主键。如Oralce 中的Sequence。
3)hilo
hi/lo 算法实现的主键生成机制,需要额外的数据库表保存主键生成历史状态。
4)seqhilo
与hilo 类似,通过hi/lo 算法实现的主键生成机制,只是主键历史状态保存在Sequence中,适用于支持Sequence的数据库,如Oracle。
5)uuid.hex
由Hibernate基于128 位唯一值产生算法生成16 进制数值(编码后以长度32 的字符串表示)作为主键。(跨数据库)
6)uuid.hex
由Hibernate基于128 位唯一值产生算法生成16 进制数值(编码后以长度32 的字符串表示)作为主键。(跨数据库)
7)guid
很少用;
8)native
根据数据库选择自动递增算法,常用;(跨数据库)
9)assigned
主键由外部程序负责生成,无需hibernate参与;
10)select
很少用;
11)foreign
使用外部表的字段作为主键。
12)sequence-identity 很少用;
13)increment
主键按数值顺序递增。此方式的实现机制为在当前应用实例中维持一个变量,以保存着当前的最大值,之后每次需要生成主键的时候将此值加1作为主键。这种方式可能产生的问题是:如果当前有多个实例访问同一个数据库,那么由于各个实例各自维护主键状态,不同实例可能生成同样的主键,从而造成主键重复异常。因此,如果同一数据库有多个实例访问,此方式必须避免使用。
一般而言,利用uuid.hex方式生成主键将提供最好的性能和数据库平台适应性。
另外由于常用的数据库,如Oracle、DB2、SQLServer、MySql 等,都提供了易用的主键生成机制(Auto-Increase 字段或者Sequence)。我们可以在数据库提供的主键生成机制上,采用generator-class=native的主键生成方式。
hibernate 的说明如下:
不过值得注意的是,一些数据库提供的主键生成机制在效率上未必最佳,大量并发insert数据时可能会引起表之间的互锁。数据库提供的主键生成机制,往往是通过在一个内部表中保存当前主键状态(如对于自增型主键而言,此内部表中就维护着当前的最大值和递增量),之后每次插入数据会读取这个最大值,然后加上递增量作为新记录的主键,之后再把这个新的最大值更新回内部表中,这样,一次Insert操作可能导致数据库内部多次表读写操作,同时伴随的还有数据的加锁解锁操作,这对性能产生了较大影响。因此,对于并发Insert要求较高的系统,推荐采用uuid.hex 作为主键生成机制。
路径:hibernate-distribution-3.3.2.GA/documentation/manual/zh-CN/html_single/index.html#mapping-declaration-id
截图:
uuid XML 配置:
<id name="id" column="id">
<generator class="uuid"/>
</id>
对应的JavaBean用String类型:
private String id;
public String getId() {
return id;
} public void setId(String id) {
this.id = id;
}
native XML 配置:
<id name="id" column="id">
<generator class="native"/>
</id>
对应的JavaBean用Integer/int类型:
private Integer id;
public Integer getId() {
return id;
} public void setId(Integer id) {
this.id = id;
}
用 MySQL 数据库,hibernate自动生成的建_student表的语句:
连接Oracle数据库进行测试:
1、重新在 hibernate.cfg.xml文件中修改Oracle的连接配置,具体配置驱动、url、username、password的配置参考:
hibernate-distribution-3.3.2.GA\project\etc\hibernate.properties
2、java bean的属性配置要符合oracle表和字段的命名规范;
3、ID 配置:
XML 的跟上面的一样;
注解:默认就是AUTO(相当于native),可以不用写,此时ID生成的sequence是hibernate_sequence;
还有 IDENTITY(只能用在MySQL和SQL Server等支持IDENTITY的数据库中,Oracle就用不了)、SEQUENCE、TABLE
@Id
@GeneratedValue(strategy=GenerationType.AUTO)
public Integer getId() {
return id;
}
3.1、如果要为 model ID 指定确定的sequence,而不是去用默认的 hibernate_sequence,配置如下:
注解:
model头:name 表示这个sequence生成器的名字,sequenceName 是指明序列在数据库中的名字
@Entity
@SequenceGenerator(name="teacherSEQ",sequenceName="teacherSEQ_DB")
ID上的配置:
@Id
@GeneratedValue(strategy=GenerationType.SEQUENCE,generator="teacherSEQ")
public Integer getId() {
return id;
}
XML:在 hibernate.cfg.xml 中的配置
<hibernate-mapping>
<class name="..." table="..." schema="...">
<id name="userId" type="java.lang.Integer">
<column name="USER_ID" precision="9" scale="0" />
<generator class="sequence">
<param name="sequence">Student_SEQ</param>
</generator>
</id>
<property ... />
</class>
</hibernate-mapping>
3.2、复杂一点的主键生成器——TableGenerator
@javax.persistence.TableGenerator(
name="Teacher_GEN",//生成器名
table="GENERATOR_TABLE",//表名
pkColumnName = "pk_key",//第一个字段,key值
valueColumnName = "pk_value",//第二个字段,value值
pkColumnValue="Teacher",//一条记录的第一个字段
allocationSize=1//增量
)
@Id
@GeneratedValue(strategy=GenerationType.TABLE,generator="Teacher_GEN")
public Integer getId() {
return id;
}
初次使用该生成器,生成器找到对应的记录,返回value值1,同时value加上对应的增量。
3.3 联合主键
XML:一个表中的两个字段做主键,例子中取Student中的id、name做主键,创建一个StudentPK做主键类,在Student中配置好联合主键
Student
package com.bjsxt.hibernate; public class Student { private StudentPK pk; private Integer age; public StudentPK getPk() {
return pk;
} public void setPk(StudentPK pk) {
this.pk = pk;
} public Integer getAge() {
return age;
} public void setAge(Integer age) {
this.age = age;
} }
StudentPK 需要实现Serializable接口,重写hashCode()和equals()方法
package com.bjsxt.hibernate; import java.io.Serializable; public class StudentPK implements Serializable{ private static final long serialVersionUID = -7950018142709463675L; private Integer id; private String name; public Integer getId() {
return id;
} public void setId(Integer id) {
this.id = id;
} public String getName() {
return name;
} public void setName(String name) {
this.name = name;
} @Override
public boolean equals(Object o) {
if(o instanceof StudentPK){
StudentPK pk = (StudentPK)o;
if(this.id == pk.getId() && this.name.equals(pk.getName())){
return true;
}
}
return false;
} @Override
public int hashCode() {
return this.name.hashCode();
}
}
Student.hbm.xml
<?xml version="1.0"?>
<!DOCTYPE hibernate-mapping PUBLIC
"-//Hibernate/Hibernate Mapping DTD 3.0//EN"
"http://hibernate.sourceforge.net/hibernate-mapping-3.0.dtd"> <hibernate-mapping package="com.bjsxt.hibernate">
<class name="Student" table="student">
<composite-id name="pk" class="com.bjsxt.hibernate.StudentPK">
<key-property name="id" />
<key-property name="name" />
</composite-id>
<property .../>
</class>
</hibernate-mapping>
插入操作:
@Test
public void testStudentSave(){
StudentPK pk = new StudentPK();
pk.setId(1);
pk.setName("zhangsan");
Student s = new Student();
s.setPk(pk);
...
}
Annotation:
第一种方法:将组件类注解为@Embeddable,并将组件的属性注解为@Id;
第二种方法:将组件的属性注解为@EmbeddedId;
第三种方法:将类注解为@IdClass,并将该实体中所有属于主键的属性都注解为@Id;
3种方法的主键类同样要需要实现Serializable接口,重写hashCode()和equals()方法。
第一种方法例子:
TeacherPK
package com.bjsxt.hibernate; import java.io.Serializable; @Embeddable
public class TeacherPK implements Serializable{ private static final long serialVersionUID = -3972276136768456123L; private Integer id; private String name; public Integer getId() {
return id;
} public void setId(Integer id) {
this.id = id;
} public String getName() {
return name;
} public void setName(String name) {
this.name = name;
} @Override
public boolean equals(Object o) {
if(o instanceof StudentPK){
StudentPK pk = (StudentPK)o;
if(this.id == pk.getId() && this.name.equals(pk.getName())){
return true;
}
}
return false;
} @Override
public int hashCode() {
return this.name.hashCode();
} }
Teacher
package com.bjsxt.hibernate; import java.util.Date; import javax.persistence.EmbeddedId;
import javax.persistence.Entity;
import javax.persistence.EnumType;
import javax.persistence.Enumerated;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;
import javax.persistence.IdClass;
import javax.persistence.SequenceGenerator;
import javax.persistence.Temporal;
import javax.persistence.TemporalType; @javax.persistence.TableGenerator(
name="Teacher_GEN",//生成器名
table="GENERATOR_TABLE",//表名
pkColumnName = "pk_key",//第一个字段,key值
valueColumnName = "pk_value",//第二个字段,value值
pkColumnValue="Teacher",//记录值
allocationSize=1//增量
) @Entity
@SequenceGenerator(name="teacherSEQ",sequenceName="teacherSEQ_DB")
public class Teacher {
private TeacherPK pk; private String title; private Date birthday; private ZhiCheng zhicheng; public String getTitle() {
return title;
} @Id
public TeacherPK getPk() {
return pk;
} public void setPk(TeacherPK pk) {
this.pk = pk;
} public void setTitle(String title) {
this.title = title;
} @Temporal(TemporalType.DATE)
public Date getBirthday() {
return birthday;
} public void setBirthday(Date birthday) {
this.birthday = birthday;
} @Enumerated(value=EnumType.STRING)
public ZhiCheng getZhicheng() {
return zhicheng;
} public void setZhicheng(ZhiCheng zhicheng) {
this.zhicheng = zhicheng;
} }
第二种方法例子:
TeacherPK
package com.bjsxt.hibernate; import java.io.Serializable; public class TeacherPK implements Serializable{ private static final long serialVersionUID = -3972276136768456123L; private Integer id; private String name; public Integer getId() {
return id;
} public void setId(Integer id) {
this.id = id;
} public String getName() {
return name;
} public void setName(String name) {
this.name = name;
} @Override
public boolean equals(Object o) {
if(o instanceof StudentPK){
StudentPK pk = (StudentPK)o;
if(this.id == pk.getId() && this.name.equals(pk.getName())){
return true;
}
}
return false;
} @Override
public int hashCode() {
return this.name.hashCode();
} }
Teacher
package com.bjsxt.hibernate; import java.util.Date; import javax.persistence.EmbeddedId;
import javax.persistence.Entity;
import javax.persistence.EnumType;
import javax.persistence.Enumerated;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;
import javax.persistence.IdClass;
import javax.persistence.SequenceGenerator;
import javax.persistence.Temporal;
import javax.persistence.TemporalType; @javax.persistence.TableGenerator(
name="Teacher_GEN",//生成器名
table="GENERATOR_TABLE",//表名
pkColumnName = "pk_key",//第一个字段,key值
valueColumnName = "pk_value",//第二个字段,value值
pkColumnValue="Teacher",//记录值
allocationSize=1//增量
) @Entity
@SequenceGenerator(name="teacherSEQ",sequenceName="teacherSEQ_DB")
public class Teacher {
private TeacherPK pk; private Integer id; private String name; private String title; private Date birthday; private ZhiCheng zhicheng; public void setName(String name) {
this.name = name;
} public String getTitle() {
return title;
} @EmbeddedId
public TeacherPK getPk() {
return pk;
} public void setPk(TeacherPK pk) {
this.pk = pk;
} public void setTitle(String title) {
this.title = title;
} @Temporal(TemporalType.DATE)
public Date getBirthday() {
return birthday;
} public void setBirthday(Date birthday) {
this.birthday = birthday;
} @Enumerated(value=EnumType.STRING)
public ZhiCheng getZhicheng() {
return zhicheng;
} public void setZhicheng(ZhiCheng zhicheng) {
this.zhicheng = zhicheng;
} }
第三种方法例子:
TeacherPK
package com.bjsxt.hibernate; import java.io.Serializable; public class TeacherPK implements Serializable{ private static final long serialVersionUID = -3972276136768456123L; private Integer id; private String name; public Integer getId() {
return id;
} public void setId(Integer id) {
this.id = id;
} public String getName() {
return name;
} public void setName(String name) {
this.name = name;
} @Override
public boolean equals(Object o) {
if(o instanceof StudentPK){
StudentPK pk = (StudentPK)o;
if(this.id == pk.getId() && this.name.equals(pk.getName())){
return true;
}
}
return false;
} @Override
public int hashCode() {
return this.name.hashCode();
} }
Teacher
package com.bjsxt.hibernate; import java.util.Date; import javax.persistence.EmbeddedId;
import javax.persistence.Entity;
import javax.persistence.EnumType;
import javax.persistence.Enumerated;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;
import javax.persistence.IdClass;
import javax.persistence.SequenceGenerator;
import javax.persistence.Temporal;
import javax.persistence.TemporalType; @javax.persistence.TableGenerator(
name="Teacher_GEN",//生成器名
table="GENERATOR_TABLE",//表名
pkColumnName = "pk_key",//第一个字段,key值
valueColumnName = "pk_value",//第二个字段,value值
pkColumnValue="Teacher",//记录值
allocationSize=1//增量
) @Entity
@SequenceGenerator(name="teacherSEQ",sequenceName="teacherSEQ_DB")
@IdClass(StudentPK.class)
public class Teacher {
private Integer id; private String name; private String title; private Date birthday; private ZhiCheng zhicheng; @Id
public Integer getId() {
return id;
} public void setId(Integer id) {
this.id = id;
} @Id
public String getName() {
return name;
} public void setName(String name) {
this.name = name;
} public String getTitle() {
return title;
} public void setTitle(String title) {
this.title = title;
} @Temporal(TemporalType.DATE)
public Date getBirthday() {
return birthday;
} public void setBirthday(Date birthday) {
this.birthday = birthday;
} @Enumerated(value=EnumType.STRING)
public ZhiCheng getZhicheng() {
return zhicheng;
} public void setZhicheng(ZhiCheng zhicheng) {
this.zhicheng = zhicheng;
} }
链接: http://pan.baidu.com/s/1qYayZk4 密码: ta5c
所需jar包链接: http://pan.baidu.com/s/1hr35oVU 密码: yhsf
hibernate_ID生成策略的更多相关文章
- 大家一起撸代码之——Hibernate各种主键生成策略与配置详解
1.assigned 主键由外部程序负责生成,在 save() 之前必须指定一个.Hibernate不负责维护主键生成.与Hibernate和底层数据库都无关,可以跨数据库.在存储对象前,必须要使用主 ...
- Hibernate各种主键生成策略与配置详解
出自:http://www.cnblogs.com/kakafra/archive/2012/09/16/2687569.html 1.assigned 主键由外部程序负责生成,在 save() 之前 ...
- hibernate主键生成策略(转载)
http://www.cnblogs.com/kakafra/archive/2012/09/16/2687569.html 1.assigned 主键由外部程序负责生成,在 save() 之前必须指 ...
- Hibernate各种主键生成策略与配置详解《转》
1.assigned 主键由外部程序负责生成,在 save() 之前必须指定一个.Hibernate不负责维护主键生成.与Hibernate和底层数据库都无关,可以跨数据库.在存储对象前,必须要使用主 ...
- Hibernate之:各种主键生成策略与配置详解
1.assigned 主键由外部程序负责生成,在 save() 之前必须指定一个.Hibernate不负责维护主键生成.与Hibernate和底层数据库都无关,可以跨数据库.在存储对象前,必须要使用主 ...
- Hibernate各种主键生成策略与配置详解【附1--<generator class="foreign">】
1.assigned 主键由外部程序负责生成,在 save() 之前必须指定一个.Hibernate不负责维护主键生成.与Hibernate和底层数据库都无关,可以跨数据库.在存储对象前,必须要使用主 ...
- 【转】Hibernate各种主键生成策略与配置详解
原文转自:Fra~~kaka's Blog 1.assigned 主键由外部程序负责生成,在 save() 之前必须指定一个.Hibernate不负责维护主键生成.与Hibernate和底层数据库都无 ...
- hibernate框架(4)---主键生成策略
主键生成策略 常见的生成策略分为六种 1.increment 由Hibernate从数据库中取出主键的最大值(每个session只取1次),以该值为基础,每次增量为1,在内存中生成主键,不依赖于底层的 ...
- Hibernate学习笔记2.4(Hibernate的Id生成策略)
通过设置告诉id该怎么设置. 1.通过xml方式 1.assigned 主键由外部程序负责生成,在 save() 之前必须指定一个.Hibernate不负责维护主键生成.与Hibernate和底层数据 ...
随机推荐
- 不带 www 跳转 到 带 www 网站..
IIS: <rule name="已导入的规则 1-1" stopProcessing="true"> <match url="^( ...
- C++_类和动态内存分配2-改进后的String类
添加前面介绍过的复制构造函数和赋值运算符,使类能够正确管理类对象使用的内存. 知道对象何时被创建和释放. =================================== 修订后的默认构造函数 ...
- 【2-SAT】【并查集】NOIp模拟题 植树方案 题解
一个类似2-SAT的思想,但是简化了很多.只需要用到并查集实现. 题目描述 企鹅国打算种一批树.所谓树,就是由$N$个结点与$N-1$条边连接而成的连通无向图.企鹅国的国王对于这些树有下列要求 ...
- CF F. MST Unification (最小生成树避圈法)
题意 给一个无向加权联通图,没有重边和环.在这个图中可能存在多个最小生成树(MST),你可以进行以下操作:选择某条边使其权值加一,使得MST权值不变且唯一.求最少的操作次数. 分系:首先我们先要知道为 ...
- HDU4499
In Chinese Chess, there is one kind of powerful chessmen called Cannon. It can move horizontally or ...
- Android 自动分析apk加固方式
本实例只对apk中lib文件夹中的文件进行分析import java.io.File;import java.io.IOException;import java.util.ArrayList;imp ...
- 基于WebImage的图片上传工具类
支持缩略图和水印. using System; using System.IO; using System.Linq; using System.Web; using System.Web.Helpe ...
- 02-使用注解配置spring
1 准备工作 1.导包 4+2+spring-aop[新版本需要导入 spring-aop 包] 2.为主配置文件引入新的命名空间(约束) [context] 3.开启使用注解代理配置文件 4.在类中 ...
- Android中的ListView点击时的背景颜色设置
想设置listview中每行在点击.选中等不同状态下有不同的背景颜色,或者背景图片. 这可以用Android的Selector来实现.它可以定义组件在不同状态下的显示方式. 新建一个xml文件list ...
- Coursera 机器学习 第7章 Support Vector Machines 学习笔记
7 Support Vector Machines7.1 Large Margin Classification7.1.1 Optimization Objective支持向量机(SVM)代价函数在数 ...