[O]SQL SERVER下有序GUID和无序GUID作为主键&聚集索引的性能表现
背景
前段时间学习《Microsoft SQL Server 2008技术内幕:T-SQL查询》时,看到里面关于无序GUID作为主键与聚集索引的建议,无序GUID作为主键以及作为聚集索引所带来的问题包括:
- 空间的浪费以及由此带来的读写效率的下降。
- 更主要的,存储的碎片化(fragmentation)以及由此带来的读写效率严重下降。
所以,尽量避免用GUID(无序或有序)做主键,不要用无序GUID做聚集索引。<摘自博友博客>
想到在工作中存在一个视图转成物理表的时候使用到了此种场景,分析了一下数据情况,已经有较多客户此表的数据将近百万级,后续会继续线性增长,而且在代码规范也强制要求不允许使用无序GUID,需要调整为有序的GUID,对于修改前后的表现,还是想做一个对比分析...
一、插入无序GUID数据
--创建表并插入无序GUID数据
--DROP TABLE T_PROORDERTYPEGUIDTEST;
create table T_PROORDERTYPEGUIDTEST (
FENTRYID varchar(36) not null default ' ',
FPROORDERENTRYID int not null default 0,
FPROORDERTYPE varchar(20) not null default ' ',
FFORMID varchar(36) not null default ' ',
FNUMBER nvarchar(160) not null default ' ',
FCREATEORGID int not null default 0,
FUSEORGID int not null default 0,
FDOCUMENTSTATUS char(1) not null default 'C',
FFORBIDSTATUS char(1) not null default 'A',
FDATE datetime not null default getdate(),
FMATERIALID int not null default 0,
FBOMID int not null default 0,
FAUXPROPID int not null default 0,
FLOT int not null default 0,
FMtoNo nvarchar(200) not null default '',
FSEQ int not null default 0,
FUNITID int not null default 0,
FPRODUCTID int not null default 0,
FWORKSHOPID int not null default 0,
FCOSTCENTERID int not null default 0,
constraint PK_PROORDERTYPE primary key (FENTRYID)
)
--插入500000条数据
declare @i int
set @i = 1
while @i < 500000
begin
INSERT INTO T_PROORDERTYPEGUIDTEST(FENTRYID,FPROORDERENTRYID,FPROORDERTYPE,FFORMID,FNUMBER,FCREATEORGID,
FUSEORGID,FDOCUMENTSTATUS,FFORBIDSTATUS,FDATE,FMATERIALID,FBOMID,FAUXPROPID,FLOT,
FSEQ,FUNITID,FPRODUCTID,FWORKSHOPID,FCOSTCENTERID) values
(NEWID(),@i,'PO','FORM_OUTSRCPROORDER','TEST00001',@i,@i,'C','A',GETDATE(),@i,@i,@i,@i,@i,@i,@i,@i,@i)
SET @i=@i+1
end ; select COUNT(1) from T_PROORDERTYPEGUIDTEST
二、插入有序GUID数据
--创建表并插入有序GUID数据
DROP TABLE T_PROORDERTYPESEQGUIDTEST;
create table T_PROORDERTYPESEQGUIDTEST (
FENTRYID uniqueidentifier not null default (NEWSEQUENTIALID()),
FPROORDERENTRYID int not null default 0,
FPROORDERTYPE varchar(20) not null default ' ',
FFORMID varchar(36) not null default ' ',
FNUMBER nvarchar(160) not null default ' ',
FCREATEORGID int not null default 0,
FUSEORGID int not null default 0,
FDOCUMENTSTATUS char(1) not null default 'C',
FFORBIDSTATUS char(1) not null default 'A',
FDATE datetime not null default getdate(),
FMATERIALID int not null default 0,
FBOMID int not null default 0,
FAUXPROPID int not null default 0,
FLOT int not null default 0,
FMtoNo nvarchar(200) not null default '',
FSEQ int not null default 0,
FUNITID int not null default 0,
FPRODUCTID int not null default 0,
FWORKSHOPID int not null default 0,
FCOSTCENTERID int not null default 0,
constraint PK_SEQPROORDERTYPE primary key (FENTRYID)
)
--插入500000条数据
declare @i int
set @i = 1
while @i < 500000
begin
INSERT INTO T_PROORDERTYPESEQGUIDTEST(FPROORDERENTRYID,FPROORDERTYPE,FFORMID,FNUMBER,FCREATEORGID,
FUSEORGID,FDOCUMENTSTATUS,FFORBIDSTATUS,FDATE,FMATERIALID,FBOMID,FAUXPROPID,FLOT,
FSEQ,FUNITID,FPRODUCTID,FWORKSHOPID,FCOSTCENTERID) values
(@i,'PO','FORM_OUTSRCPROORDER','TEST00001',@i,@i,'C','A',GETDATE(),@i,@i,@i,@i,@i,@i,@i,@i,@i)
SET @i=@i+1
end ; select COUNT(1) from T_PROORDERTYPESEQGUIDTEST
三、分析索引碎片
--分析索引碎片
declare @table_id int
set @table_id=object_id('T_PROORDERTYPEGUIDTEST')
dbcc showcontig(@table_id);
DBCC SHOWCONTIG 正在扫描 'T_PROORDERTYPEGUIDTEST' 表...
表: 'T_PROORDERTYPEGUIDTEST' (410536596);索引 ID: 1,数据库 ID: 8
已执行 TABLE 级别的扫描。
- 扫描页数................................: 13933
- 扫描区数..............................: 1759
- 区切换次数..............................: 13932
- 每个区的平均页数........................: 7.9
- 扫描密度 [最佳计数:实际计数].......: 12.50% [1742:13933]
- 逻辑扫描碎片 ..................: 99.22%
- 区扫描碎片 ..................: 0.11%
- 每页的平均可用字节数.....................: 2569.6
- 平均页密度(满).....................: 68.25%
DBCC 执行完毕。如果 DBCC 输出了错误信息,请与系统管理员联系。
declare @table_id int
set @table_id=object_id('T_PROORDERTYPESEQGUIDTEST')
dbcc showcontig(@table_id)
DBCC SHOWCONTIG 正在扫描 'T_PROORDERTYPESEQGUIDTEST' 表...
表: 'T_PROORDERTYPESEQGUIDTEST' (1114539104);索引 ID: 1,数据库 ID: 8
已执行 TABLE 级别的扫描。
- 扫描页数................................: 8197
- 扫描区数..............................: 1033
- 区切换次数..............................: 1032
- 每个区的平均页数........................: 7.9
- 扫描密度 [最佳计数:实际计数].......: 99.23% [1025:1033]
- 逻辑扫描碎片 ..................: 0.67%
- 区扫描碎片 ..................: 0.10%
- 每页的平均可用字节数.....................: 44.3
- 平均页密度(满).....................: 99.45%
DBCC 执行完毕。如果 DBCC 输出了错误信息,请与系统管理员联系。
四、占用空间情况
sp_spaceused 'T_PROORDERTYPEGUIDTEST';

sp_spaceused 'T_PROORDERTYPESEQGUIDTEST';

五、查询执行情况
select * from T_PROORDERTYPEGUIDTEST ;
select * from T_PROORDERTYPESEQGUIDTEST ;

再分别插入50W数据
declare @i int
set @i = 1
while @i < 500000
begin
INSERT INTO T_PROORDERTYPEGUIDTEST(FENTRYID,FPROORDERENTRYID,FPROORDERTYPE,FFORMID,FNUMBER,FCREATEORGID,
FUSEORGID,FDOCUMENTSTATUS,FFORBIDSTATUS,FDATE,FMATERIALID,FBOMID,FAUXPROPID,FLOT,
FSEQ,FUNITID,FPRODUCTID,FWORKSHOPID,FCOSTCENTERID) values
(NEWID(),@i,'PO','FORM_OUTSRCPROORDER','TEST00001',@i,@i,'C','A',GETDATE(),@i,@i,@i,@i,@i,@i,@i,@i,@i)
SET @i=@i+1
end ; declare @i int
set @i = 1
while @i < 500000
begin
INSERT INTO T_PROORDERTYPESEQGUIDTEST(FPROORDERENTRYID,FPROORDERTYPE,FFORMID,FNUMBER,FCREATEORGID,
FUSEORGID,FDOCUMENTSTATUS,FFORBIDSTATUS,FDATE,FMATERIALID,FBOMID,FAUXPROPID,FLOT,
FSEQ,FUNITID,FPRODUCTID,FWORKSHOPID,FCOSTCENTERID) values
(@i,'PO','FORM_OUTSRCPROORDER','TEST00001',@i,@i,'C','A',GETDATE(),@i,@i,@i,@i,@i,@i,@i,@i,@i)
SET @i=@i+1
end ;

参考文章
http://msdn.microsoft.com/zh-cn/library/ms175008(v=sql.90).aspx
http://msdn.microsoft.com/zh-cn/library/ms188776.aspx
http://www.sqlskills.com/blogs/kimberly/disk-space-is-cheap/
http://www.cnblogs.com/zhouruifu/archive/2012/04/18/2454088.html
Microsoft SQL Server 2008技术内幕:T-SQL查询
[O]SQL SERVER下有序GUID和无序GUID作为主键&聚集索引的性能表现的更多相关文章
- SQL SERVER下有序GUID和无序GUID作为主键&聚集索引的性能表现
背景 前段时间学习<Microsoft SQL Server 2008技术内幕:T-SQL查询>时,看到里面关于无序GUID作为主键与聚集索引的建议,无序GUID作为主键以及作为聚集索引 ...
- SQL Server 2014新特性探秘(3)-可更新列存储聚集索引
简介 列存储索引其实在在SQL Server 2012中就已经存在,但SQL Server 2012中只允许建立非聚集列索引,这意味着列索引是在原有的行存储索引之上的引用了底层的数据,因此会 ...
- SQL Server下实现利用SQL Server Agent Job对索引重建实现Balance Load
昨天工作中遇到这样一个场景,有个项目需要把某台服务器下所有的表和索引都启用数据压缩(data_compression=page),已经启用了的表和索引就不需要再压缩一次了.统计一下后发现要运行的REB ...
- Microsoft SQL Server下的SQL语句
SQL语句先前写的时候,很容易把一些特殊的用法忘记,我特此整理了一下SQL语句操作.一.基础 1.说明:创建数据库CREATE DATABASE database-name 2.说明:删除数据库dro ...
- ACCESS与SQL Server下SQL Like 查询的不同
在ACCESS中LIKE的用法Access里like的通配符用法是这样: “?”表示任何单一字符: “*”表示零个或多个字符: “#”表示任何一个数字 所以应该是: select * from dat ...
- SQL Server下ADO.NET 怎么获取数据库SQL语句INSERT,UPDATE,DELETE了多少行数据
ADO.NET 在发送SQL语句到SQL Server数据库后,怎么知道真正INSERT,UPDATE,DELETE了多少行数据呢? 使用SQL Server内置的全局变量@@ROWCOUNT即可,@ ...
- SQL SERVER中用户定义标量函数(scalar user defined function)的性能问题
用户定义函数(UDF)分类 SQL SERVER中的用户定义函数(User Defined Functions 简称UDF)分为标量函数(Scalar-Valued Function)和表值函数(T ...
- Sql Server Analysis Service 处理时找到重复的属性键、找不到属性键错误(转载)
这是两个非常常见的SSAS处理异常,网上也能找到很多文章讲解决办法,但很少见关于异常原因的分析,先来看看第一个" OLAP 存储引擎中存在错误: 处理时找到重复的属性键",一个维度 ...
- 三、Sql Server 基础培训《进度3-是否使用外键(知识点学习)》
学习作业3: 问题1:你觉得外键有哪些适用情况?哪些不适用情况? 问题2:本次实战案例,由你来架构,你觉得有必要建立外键吗? 说明你的理由? ======================= ...
随机推荐
- Kettle文本文件输出和输入控件使用中,换行符导致的问题处理
1.如下图通过输入控件从数据库读取数据然后生成TXT文本文件,TXT文件生成原则是每一条数据生成一行数据,第二条数据换行保存 2.如下图所示,使用文本文件输入控件读入上图生成的文件,文件读入原则是按行 ...
- winPcap编程之不用回调方法捕获数据包(五 转)
这一次要分析的实例程序跟上一讲非常类似(“打开适配器并捕获数据包”),略微不同的一点是本次将pcap_loop()函数替换成了pcap_next_ex()函数.本节的重点也就是说一下这两个函数之间的差 ...
- C#枚举中使用Flags特性
如果对一个值可以包含多个,那么可以使用枚举,加上Flags 本文告诉大家如何写一个 Flags. 在写前,需要知道一些基础知识,取反.或.与,如果不知道的话,请去看看基础. 当然,这些太复杂了,我也不 ...
- 正六边形网格化(Hexagonal Grids)原理与实现
在路径规划.游戏设计栅格法应用中,正六边形网格不如矩形网格直接和常见,但是正六边形具有自身的应用特点,更适用于一些特殊场景中,比如旷阔的海洋.区域或者太空.本文主要讲述如何对正六边形进行几何学分析.网 ...
- 在centos6上实现LAMP的FPM模式
原理 http使用一次编译法编译安装,php独立服务fpm实现. 软件版本 在本次实验中,我们需要用到的软件版本如下: apr-1.6.2 apr-util-1.6.0 httpd-2.4.28 ma ...
- Python3处理HTML获取所需内容
处理HTML页面,经常使用的便是使用beautifulsoup库 pip install beautifulsoup4 执行上述语句下载bs4库 一般请求下来的所需数据都位于tbody的tr标签里,下 ...
- PHP垃圾回收机制
一.引用计数基本知识 每个php变量存在一个叫"zval"的变量容器中,当一个变量被赋常量值时,就会生成一个zval变量容器.一个zval变量容器,除了包含变量的类型和值,还包括两 ...
- PhiloGL学习(6)——深情奉献:快乐的一家
前言 话说上一篇文章结尾讲到这一篇要做一个地球自转以及月球公转的三维动画,提笔,不对,是提键盘开始写的时候脑海中突然出现了几年前春晚风靡的那首歌:蒙古族小丫头唱的快乐的一家.闲言莫提,进入正题. ...
- hdu 6215 -- Brute Force Sorting(双向链表+队列)
题目链接 Problem Description Beerus needs to sort an array of N integers. Algorithms are not Beerus's st ...
- Jquery datatable中文排序问题
先扩展datatable的的排序功能,添加一个自定义排序函数 //为jq datatable 自定义中文排序 jQuery.fn.dataTableExt.oSort['chinese-sort-as ...