- 浏览: 660467 次
- 性别:
- 来自: 常州
文章分类
- 全部博客 (345)
- java (63)
- Struts2 (11)
- Spring2.5 + (17)
- Hibernate (25)
- Struts2 Spring hibernate (5)
- log4j (3)
- apache tomcat (12)
- oracle (22)
- oracle_存储过程 (4)
- mysql (18)
- jquery (11)
- prototype (5)
- js (19)
- quartz (5)
- 设计模式 (6)
- eclipse/MyEclipse 注意事项 (9)
- eclipse (0)
- css (6)
- 正则表达式 (2)
- linux (18)
- PHP (6)
- 多线程 (20)
- XML (1)
- jstl (3)
- mongoDB (7)
- android (20)
- 反射 (1)
- IOS (46)
- SVN (3)
- C/C++ (4)
- 百度地图 (2)
- IO/SOCKET (3)
- 百度地图JS (1)
- 树莓派/香蕉派 (1)
最新评论
-
anny101:
想转发一下,不知道怎么转发。评论一下吧。方便查看。
fetch = FetchType.EAGER 作用 -
Navee:
果然我这也是是防火墙问题
解决 Linux 安装 httpd局域网无法访问 -
dhyang909:
...
oracle 10g+ 行列转换 -
国产希特勒:
真强,居然有人把公司的面试题挂到javaeye上了
锦江国际的一道面试题(很简单) -
tomfish88:
比如我要拦截不同业务的service类里面的方法 @Poi ...
Spring AOP annotation 拦截表达式 分析
请您先登录,才能继续操作
转的:
今天上班,发现一个同事用oracle的sys_guid()来做从一个表中随机获取6条记录:
select * from (select * from tablename order by sys_guid()) where rownum < 7;
看得出来是先创建guid,然后将表记录按照这个guid排序,再从中取头6条。
数据库主键用guid我倒是见过,这样用作取随机数倒是头一次碰上。
立刻又想到oracle用guid作主键,跟sequnce比较哪个更好。google中还是找到了一篇文章说的比较好:
http://sgsoft.itpub.net/post/28147/270097
最近又有朋友争论起 SYS_GUID 与 sequence 谁做主键更合适的问题。下面我以一个案例说明一下,两者在实际应用中的情况。以下内容纯属个人研究,观点亦仅限于本案例
记得A项目组是一个物流管理系统,后台采用了Oracle数据库。在系统中的核心表托运单表中,关于主键采用何种数据类型,是 sequence 还是用GUID , 大家起了争论。
从网络搜索得到的结论看,一般的意见总结为:
1.
SYS_GUID()比sequence复杂;
2.SYS_GUID做主键,则表、索引存储开销多;
3.SYS_GUID索引查询比sequence慢;
下面对SYS_GUID和Sequence做主键的情况进行以下对比.
edl@PISC> select count(*) from all_objects;
COUNT(*)
----------
50231
已用时间 : 00: 00: 02.52
创建下列对象:
create table tsg as select RAWTOHEX(sys_guid()) sgid,a.* from all_objects a;
create SEQUENCE seq_tsg;
create table tsg2 as select seq_tsg.nextval,a.* from all_objects a;
空间比较
现在这两个表:tsg和tsg2拥有的行数相同,但大小不同:
表 |
行数 |
Number Extents |
Size in bytes |
索引大小 |
TSG(SYS_GUID主键) |
50231 |
23 |
8388608 |
3145728 |
TSG2(Sequence主键) |
50231 |
21 |
6291456 |
917504 |
换言之 , 相同条件下 , 使用 SYS_GUID 做主键比用 Sequence 做主键 ,表 多消耗了空间 2097152 byte, 索引多消耗2228224 byte, 平均每行多消耗86.1 byte.
考虑到生产环境下, 每天5 万条记录, 则一年365*50000=18250000 条记录, 则理论上需要多耗费空间约合 1.43GB 存储空间. 这些空间对磁盘消耗而言可以忽略不计,对内存仍然是有一定影响的,但就当前的服务器能力而言,影响有限,如果对表进行合理分区后,这种影响可以降低至极低。
执行计划比较
比较唯一查询时的执行计划:
对TSG 执行:
select owner
from tsg
where sgid = 'F36C09B7A7A84297995352D2409EB40E'
对TSG2 执行:
select owner
from tsg2
where sgid = 99
执行计划比较如下:
统计信息对比:
从以上统计信息看,
执行计划相同。
可以预料到的是,
由于使用SYS_GUID
做主键,
比较的是字符串,
故耗费CPU
要高些,
因此,logical reads
要高些,
至于Physical Readers
居然低一些,
就不知道原因了(实际上二者基本都没有产生大量的物理读),
估计是我的测试环境Db Cache
太小的缘故.
对于响应时间, 这应该是计算机环境产生的影响, 不能说明问题,这两条语句响应都很快, 小于0.02 秒.
小结
从实践来看, 使用SYS_GUID() 做主键的优点多于负面影响。特别是在多个数据库数据集成时,GUID 的优点显而易见. A项目最终没有采用客户定义的“货单唯一序号”作为主键,也是出于关系数据库设计的法则约定:“主键不要代表任何意义”。
综上所述,SYS_GUID 做主键:
SYS_GUID 比sequence 复杂=== è 有限范围的正确 :由于SYS_GUID 是RAW 类型的,做主键是,需要使用 RAWTOHEX 或者HEXTORAW 类的函数转换,若直接使用,则需要建立函数索引等。但这种复杂性往往在前端业务系统中体现不出,主键常常作为隐含的唯一ID 去标识对象,而不显示出来(或者不手工操作它,因为它无意义)。
SYS_GUID 做主键存储开销大= è 不需要评估系统规模:如今存储非常便宜,内存也足够大,如果2 千万条记录增加不到1.5G内存的话,当前普通的服务器已经可以承受,如果进行合理分区,则影响可以降低到极低。当然,如果您的服务器资源很紧张,那恐怕得放弃使用SYS_GUID
SYS_GUID 做主键查询比 sequence 慢 è 不正确:实践证明,二者是一样的。
发表评论
-
oracle exception 的 传播
2012-11-29 19:39 1092没研究出来oracle exception ... -
存储过程调存储过程的事务
2012-11-28 19:49 1122直接上代码: 是在包里写的存储过程,要测试的话,要先写 ... -
声明一个含有某张表不具备字段的游标
2012-11-22 15:28 1061其中,data.*是一张表,然后把其他表中的字段也加到sal_ ... -
每天凌晨清空sequence,让sequence每天从1开始
2012-11-22 15:18 2426用SQL命令行: job: variable job nu ... -
oracle 存储过程知识点
2012-10-18 23:50 1110第一个简单的存储过程: create or replace ... -
oracle 10g+ 行列转换
2012-08-18 23:30 1271WITH t AS( SELECT 1 AS sno, ... -
检查空表
2012-08-08 17:00 99611g导出数据的时候,空表导不出来,所以要检查空表 ... -
删除oracle10G
2012-07-27 15:12 1006软件环境: 1、Windows XP + Oracle 1 ... -
oracle 报表 自己备份用
2012-04-27 16:23 1100上个月做的报表 记下这个SQL文,以后还要用。 sel ... -
oracle 小知识点
2012-04-27 15:58 1018如果a.Num为null,那么就取后面的0 nvl(a.Nu ... -
oracle 判断 数据是否为数字
2012-04-16 19:50 1245SELECT * FROM t a WHERE len ... -
oracle 判断 数据重复
2012-03-30 19:38 1058select AUNAME from CLUB_A ... -
oracle 添加删除 某个字段,并添加注释
2011-11-07 15:25 2063oracle添加某个字段,并添加注释: alte ... -
PowerDesigner 的反向工程
2011-09-15 14:31 1378有的时候要分析别人的数据库 但看表不能很好的体现业务逻辑 ... -
oracle 数据重复,只取一条
2011-03-11 13:48 6875oracle中重复记录只取其中一条 select * f ... -
oracle 转换日期
2011-03-03 21:53 940TO_DATE('2011-02-22 10:38:50',' ... -
oracle 一次插入多条
2011-01-17 19:22 1126insert into test1 (TID, TNAME) ... -
oracle获取随机记录
2011-01-12 15:29 1079oracle获取随机记录 select * from (sel ... -
oracle 的一些命令
2011-01-11 17:27 984解锁scott账户 先用DBA进入SQLPLUS sqlplu ... -
oracle 导入导出
2010-11-25 11:24 681转的 exp本地导出与imp本地导入 exp命令: 1 e ...
相关推荐
seqhilo是一种通过hilo算法实现的主键生成策略,但是主键历史保存在Sequence中。这种策略适用于支持Sequence的数据库,如Oracle。 increment increment是一种插入数据的时候hibernate会给主键添加一个自增的主键的...
除了使用序列实现自增主键外,Oracle还提供了其他几种主键生成策略,比如使用`SYS_GUID()`函数生成全局唯一标识符(GUID)作为主键。这种方法适用于需要全局唯一性的场景,但可能不适合对性能要求较高的应用,因为`...
- **描述**:通过调用数据库的 Sequence 对象来生成主键,需要显式指定 Sequence 名称。 - **应用场景**:在 Oracle 数据库中常见,因为 Oracle 不支持自增字段,而 Sequence 是一种高效的解决方案。 #### 5. ...
- [Oracle序列文档](https://docs.oracle.com/en/database/oracle/oracle-database/19/sqlrf/CREATE-SEQUENCE.html#GUID-D3178A7D-13B4-426D-830F-BE78A74E7631) - [Hibernate hbm2ddl属性详解]...
- **描述**:`native`策略根据所使用的数据库选择最适合的主键生成策略,可能是`identity`、`sequence`或`hilo`之一。 - **应用场景**:适用于需要灵活适应不同数据库环境的场景。 #### 9. `assigned` - **描述**...
2. 不支持自动增加的数据库,如Oracle,通常使用序列(Sequence)生成主键。在这种情况下,可以使用`<selectKey>`元素。例如: ```xml SELECT stu_seq.nextval FROM dual ``` 这里`order="BEFORE"`表示在...
在上面的示例代码中,创建了一个名为 `Car` 的表,包含三个字段:`GUID`、`PhoneId` 和 `UserName`,其中 `GUID` 字段是主键。 序列(Sequence)是一种数据库对象,用于生成唯一的数字标识符。序列可以用于生成主键...
7. **@GenericGenerator**: 提供了更多的主键生成策略,包括`native`, `uuid`, `hilo`, `assigned`, `identity`, `select`, `sequence`, `seqhilo`, `increment`, `foreign`, `guid`, `uuid.hex`, 和 `sequence-...
Native策略根据当前使用的数据库类型自动选择最合适的主键生成策略(如Identity、Sequence或Hilo)。 **特点:** - 自动适应不同类型的数据库。 - 提供了较好的灵活性和可移植性。 - 无需在配置文件中明确指定生成...
在.NET开发中,当需要与Oracle数据库交互时,特别是处理自增主键ID的情况,可能会遇到一些挑战。在SQL Server中,我们可以轻松设置一个自动增长的Identity列来处理这一问题,但在Oracle数据库中,我们需要采取不同的...
CREATE SEQUENCE sequence_student INCREMENT BY 1 START WITH 1 NOMAXVALUE NOCYCLE CACHE 10; ``` 在这个例子中,`INCREMENT BY 1`表示每次调用时序列值递增1;`START WITH 1`表示起始值为1;`NOMAXVALUE`表示...
- **添加主键约束**: 示例`alter table class add constraint class_key primary key (classid)`。 #### 十、自动增长与GUID - **自增长序列**: - 创建序列: `create sequence student_sequence increment by 1 ...
- **sequence**: 使用数据库序列生成主键。 - **hilo**: 使用高/低位算法。 - **seqhilo**: 结合sequence和hilo算法。 - **guid**: 生成全局唯一标识符。 - **uuid**: 生成UUID。 - **native**: 根据不同的...
Ibatis提供了多种主键生成策略,比如`identity`(标识列,适用于自动增长类型)、`sequence`(序列,Oracle常用)和`guid`(全局唯一标识符)。在Oracle环境下,我们通常会创建一个序列对象,然后在映射文件中配置...
5. **主键策略**:MBG可以根据数据库表的主键类型自动选择合适的主键生成策略,如Identity(自动增长)、Sequence(序列)或Guid(全局唯一标识符)。 6. **逆向工程**:MBG的逆向工程功能意味着它可以分析数据库...
5. **主键策略**:MyBatis 提供了几种主键生成策略,如 Identity(自动增长)、Sequence(序列)、Guid(全局唯一标识符)等,可以根据数据库类型和需求选择合适的策略。 6. **自定义模板**:如果默认生成的代码不...
- **Code**:使用GUID(全局唯一标识符)作为序列的唯一代码,类型为Varchar,长度50。 - **FullName**:存储序列的全名,类型为Varchar,长度100。 - **Prefix**:序列号的前缀,如“SEQ_”,类型为Varchar,...
例如,在MySQL中,可以通过在表的主键列上使用`AUTO_INCREMENT`属性来实现。 ```xml ``` 2. **Native**: 此策略允许Hibernate选择最佳的标识符生成策略,这通常取决于底层数据库的特性。 ```xml ...
Hibernate提供了多种主键生成策略,如increment、identity、sequence、guid、native等,可以根据数据库特性选择合适的策略。 6. 对象状态管理: Hibernate管理的对象有四种状态:瞬时态、持久态、脱管态和临时态...