本文分为两个问题: 第一,碎片是什么;第二,碎片怎么处理;

现在,来找解决这两个问题:

 一、碎片是什么

说到碎片,就要提到索引了,索引用着挺爽的啊!是的,一旦索引建立,我们搜索数据的效率就提高了;然后我们就要想一想了,索引将我们的数据排序了,不管聚集还是非聚集索引总归是将数据排序了。这些数据给排序了,那么问题来了,我们个这些已经排序的数据进行插入操作会产生什么后果?人家本来好好排着队呢!插队的来了!

假设一群很瘦的人在排队,突然插入一个胖子,且不说胖子捣乱了正常的排序规则,胖子插进队伍中,一个人占了两个人的空间,这个时候对于瘦的人来说,胖子浪费了一个人的空间,如果不断的有胖子插队,浪费的空间会越来越多。浪费的空间在数据库中就是碎片!这里有一篇博客,举例说明了在数据库中碎片的产生。在数据库中,数据存在于页内,一个页是8K,索引已经建立的前提下,这8K数据是好好的排序待着的,然后,向这个页中插入一条数据(比原来数据中最大行还要大),这时后面数据就会遵循B树规则开始移动,因为这个页已经满了,后面的数据就会被挤出去若干条到下一页,如果下一页也是满的,依次往下排,这对于数据库来说消耗是很大的。这个过程中,在最初的页中,就会产生碎片,因为插入的数据偏大,导致后面的数据后移到别人页,就会空出空间了,而这部分空间就暂时没法利用,造成碎片。这种情况属于内部碎片,是页内的。因为在这个区中可能,页与页之间还是连续的。仅仅是最初的那个页中的数据是断续的。首先,插入数据造成数据移动消耗大,另外,在页中打乱了页内的排序,造成查询性能下降。这就是碎片造成影响。

另一种,情况就是插入的数据使页与页之间造成断续,比如,插入的数据正好在页中最后一行,被挤出到别的页的数据,与原来的页之间没有了连续,这后果就更严重了,这种情况就是外部的碎片。

这样看,在一定程度上索引的性能就下降了。就需要重新维护索引了。怎么维护呢?将原来的索引删除,重新构建?这种做法,在某些场景中是很合适的。比如,插入的动作比较少的情况下,在合适的时候,重现构建索引是可取的。除了,重构呢?

 二、碎片怎么处理

    我们要进行索引的维护,首先要知道一些查询数据库性能的语句,来获取当前数据库的性能,做出判断之后,采取不同的措施。

此时我们用到的就是元数据函数sys.dm_db_index_physical_stats,它有助于确定数据库中的页和区段有多满。使用这个函数得到当前数据的一些性能信息。图片来源于参考博客。

下面,先来说第一种类似于重建:

          1、使用DROP_EXISTING语句重建索引:为了避免重建两次索引,使用DROP_EXISTING语句重建索引,因为这个语句是原子性的,不会导致非聚集索引重建两次,但同样的,这种方式也会造成阻塞。缺点:阻塞:与卸载重建方法类似,这种技术也导致并面临来自其他访问该表(或该表的索引)的查询的阻塞问题。、

使用约束的索引:与卸载重建不同,具有DROP_EXISTING子句的CREATE INDEX语句可以用于重新创建使用约束的索引。如果该约束是一个主键或与外键相关的唯一性约束,在CREATE语句中不能包含UNIQUE。

具有多个碎片化的索引的表:随着表数据产生碎片,索引常常也碎片化。如果使用这种碎片整理技术,表上所有索引都必须单独确认和重建。

CREATE UNIQUE CLUSTERED INDEX IX_C1 ON t1(c1)
WITH (DROP_EXISTING = ON)

 2、用ALTER INDEX REBUILD语句重建索引:使用这个语句同样也是重建索引,但是通过动态重建索引而不需要卸载并重建索引.是优于前两种方法的,但依旧会造成阻塞。可以通过ONLINE关键字减少锁,但会造成重建时间加长。

  阻塞:这个依然有阻塞问题。

事务回滚:ALTER INDEX REBUILD完全是一个原子操作,如果它在结束前停止,所有到那时为止进行的碎片整理操作都将丢失,可以通过ONLINE关键字减少锁,但会造成重建时间加长。

3、使用ALTER INDEX REORGANIZE:这种方式不会重建索引,也不会生成新的页,仅仅是整理叶级数据,不涉及非叶级,当遇到加锁的页时跳过,所以不会造成阻塞。但同时,整理效果会差于前三种。

     4、填充因子:填充因子的概念可以理解为预留一定的空间存放插入和更新新增加的数据,以避免页拆分。  填充因子值的选择:

 如何设置填充因子的值并没有一个公式或者理念可以准确的设置。使用填充因子虽然可以减少更新或者插入时的分页,但同时因为需要更多的页,所以降低了查询的性能和占用更多的磁盘空间.如何设置这个值进行trade-off需要根据具体的情况来看。具体情况要根据对于表的读写比例来看,我这里给出我认为比较合适的值:

  1. 当读写比例大于100:1时,不要设置填充因子,100%填充
  2. 当写的次数大于读的次数时,设置50%-70%填充
  3. 当读写比例位于两者之间时80%-90%填充

本文参考: SQL Server索引的维护 - 索引碎片、填充因子 <第三篇>

 
 

SQL Server 性能篇- 碎片的更多相关文章

  1. 改进SQL Server 性能 - 索引碎片重建

    我们先来看一个用户表上的索引碎片情况: DBCC SHOWCONTIG scanning 'Lead' table...Table: 'Lead' (1422628111); index ID: 1, ...

  2. SQL Server 性能优化详解

    故事开篇:你和你的团队经过不懈努力,终于使网站成功上线,刚开始时,注册用户较少,网站性能表现不错,但随着注册用户的增多,访问速度开始变慢,一些用户开始发来邮件表示抗议,事情变得越来越糟,为了留住用户, ...

  3. 【目录】sql server 进阶篇系列

    随笔分类 - sql server 进阶篇系列 sql server 下载安装标记 摘要: SQL Server 2017 的各版本和支持的功能 https://docs.microsoft.com/ ...

  4. 初涉SQL Server性能问题(4/4):列出最耗资源的会话

    在上3篇文章里,我们讨论了列出反映服务器当前状态的不同查询. 初涉SQL Server性能问题(1/4):服务器概况 初涉SQL Server性能问题(2/4):列出等待资源的会话 初涉SQL Ser ...

  5. 初涉SQL Server性能问题(3/4):列出阻塞的会话

    在 初涉SQL Server性能问题(2/4)里,我们讨论了列出等待资源或正运行的会话脚本.这篇文章我们会看看如何列出包含具体信息的话阻塞会话清单. /************************ ...

  6. SQL Server 性能调优培训引言

    原文:SQL Server 性能调优培训引言 大家好,这是我在博客园写的第一篇博文,之所以要开这个博客,是我对MS SQL技术学习的一个兴趣记录. 作为计算机专业毕业的人,自己对技术的掌握总是觉得很肤 ...

  7. SQL Server 性能优化之——系统化方法提高性能

    SQL Server 性能优化之——系统化方法提高性能 阅读导航 1. 概述 2. 规范逻辑数据库设计 3. 使用高效索引设计 4. 使用高效的查询设计 5. 使用技术分析低性能 6. 总结 1. 概 ...

  8. sql server 性能调优之 资源等待 LCk

    一.  概述 这次介绍实例级别资源等待LCK类型锁的等待时间,关于LCK锁的介绍可参考 “sql server 锁与事务拨云见日”.下面还是使用sys.dm_os_wait_stats 来查看,并找出 ...

  9. sql server性能调优

    转自:https://www.cnblogs.com/woodytu/tag/%E6%80%A7%E8%83%BD%E8%B0%83%E4%BC%98%E5%9F%B9%E8%AE%AD/defaul ...

随机推荐

  1. mysql之7xtrabackup

    目录: 1.前言 2.环境 3.开始备份 3.1.innobackupex介绍 3.2.一次完全备份 3.3.一次完全恢复 3.4.增量备份 3.5.增量备份的恢复过程 1.前言: Xtrabacku ...

  2. 对$NOMOD51的理解

    很多朋友在看asm代码的时候,对下面的语句不是很了解,下面解说一下. $NOMOD51 $INCLUDE (REG932.INC) 解释:$NOMOD51,这一指令功能是使A51不识别8051的所有预 ...

  3. 在 .pro里加入 QMAKE_CXXFLAGS += /MP 将并行编译,加快编译速度(姚冬的办法)

    但是只对VC编译器有效果. 另外还可以自己设置stdafx.h文件 http://www.zhihu.com/question/23045749

  4. 360云后台(使用HTTP Cache服务器)

    工作职责:设计优化HTTP Cache服务器,负载均衡服务器,调度系统等核心系统开发优化CDN系统架构满足流量.性能.成本要求 技能要求: 精通Linux, C/C++语言,HTTP协议精通高性能服务 ...

  5. mysql服务的注册,启动、停止、注销。 [delphi代码实现]

    unit Service; interface uses Windows,Classes,SysUtils,Winsvc,winsock; Type {服务句柄信息} TScmInfo=Record ...

  6. Match类

    Regex在匹配的时候,常常会返回一个Match类的对象,今天就来看看怎么玩这个对象. 一.属性 Captures 按从里到外.从左到右的顺序获取由捕获组匹配的所有捕获的集合(如果正则表达式用 Reg ...

  7. 狗屎的asp.net core 果然发生了重大的变更

    狗屎的asp.net core  果然发生了重大的变更 ....仔细看官方的文档,想骂娘....你发布版本的时候,能不能先想好先设计好再发布?朝三暮四...大撒笔....你老这样变来变去,谁还敢碰你啊 ...

  8. Java安装根目录

    bin存放了Java的操作工具,比如编译工具javac.启动JVM的Java等 db存放了Java测试的数据库Derby,企业不用 include存放C++的头文件 jre运行环境,里面有JVM li ...

  9. Unity 2DSprite

    Unity官方意识到在4.3版本之前,并没有自带的支持2D游戏工具,商店里面有很多有名2D插件Uni2D,2DToolkit,在4.3版本之后就出现UISprite精灵来支持2D游戏开发,我用这个很多 ...

  10. char与byte的差别

    非常多刚開始学习的人(包含我,已经学了一年多java了)肯会对char和byte这两种数据类型有所疑惑,相互混淆,今天特地查了好多资料,对byte和char两种数据类型进行了总结和比較,先将结果与大家 ...