索引初探(三)

由于前一篇写的有点匆忙很多地方不是很简单,这一片再描述一些概念和细节。

首先,我们都知道在数据库中的存储分为两种结构,一是堆;二是B树。堆的数据是没有排序也就没有结构性可言,我们可以简单理解为没有索引的表数据就是以堆的形式存在的。与之相对的,索引都是B树的形式存储,这样的话索引中数据是有序排列的。

其次,索引的结构上篇也是讲了,我们这里再根据非聚集索引的结构来对比一下聚集索引。

如图(官方提供的非聚集索引的结构图):

我们不难看出,上面红色标注的是非聚集索引,下面是聚集索引或者堆。由这个图来分析:

1.非聚集索引与聚集索引一样都是B树结构。

2.非聚集索引的叶子节点不是数据页,这样非聚集索引的叶子节点只包含键值和定位符(定位符,存在两种可能,如果表中有了聚集索引那么定位符就是个直接指向数据所在行的物理指针,如果有聚集索引,那么就是一个指向索引的聚集键)

3.与聚集索引不同,非聚集索引本身并不会改变数据页的存储模式。

本篇的重点:非聚集索引

非聚集索引包含了索引键列,包含列和书签。书签的值根据所在表是堆还是聚集索引既可以是RID也可以是聚集索引键,我们用两个图对比看一下一目了然。

上图显示的是非聚集索引在对上的实际结构,可以发现除了索引键值外,就是“RID”就是指向数据页的指针。

上图是非聚集索引在聚集索引上的结构,可以发现除去索引键值外,就是聚集索引键,查询数据时继续到索引中去寻找数据。

那么非聚集索引的优点:

1、因为在SQL Server中一页只是8K,页面空间有限,所以一行所包含的列数越少,它能保存的行就越多。非聚集索引通常不包含表中所有的列,它一般只包含非常少数的列。因此,一个页上将能包含比表行(所有的列)更多行的非聚集索引。

2、非聚集索引的另一个好处是,它有一个独立于数据表的结构,所以可以被放置在不同的文件组,使用不同的I/O路径,这意味着SQL Server可以并行访问索引和表,使查找更快速。

3、与聚集索引不同的时,一个表中可以有多个非聚集索引增加查询覆盖和交叉等等可以提高查询速度。

通过对聚集和非聚集索引的描述大概了解两种索引的基本结构和优缺点,下面根据其他人总结的什么情况下建立何种索引的一个常规方式:

                           使用聚集索引      使用非聚集索引 外键列                          应                      应 主键列                          应                      应 列经常被分组排序             应                     应 返回某范围内的数据          应                   不应 小数目的不同值               应                    不应 大数目的不同值               不应                   应 频繁更新的列                 不应                    应 频繁修改索引列              不应                    应 一个或极少不同值           不应                    应

总结:

通过对索引的介绍和测试,我们发现索引能大幅提高查询的效率,但是同样相应的维护成本和性能消耗也是非常大的,这需要我们根据实际情况进行合理的设计。 当一个查询被传到数据引擎时,SQL Server可以通过三种路径获取数据来满足这个查询。

  1.     不需要访问表仅需要访问索引本身,这种情况必须是索引覆盖了请求所包含的列
  2.     使用索引键值去访问非聚集索引,然后使用书签访问非聚集索引所在表
  3.     全表扫描来获取数据

    了解这些基础概念接下来我们将从实际应用中去解决如何优化、如何合理化使用索引。

本文参与腾讯云自媒体分享计划,欢迎正在阅读的你也加入,一起分享。

发表于

我来说两句

0 条评论
登录 后参与评论

相关文章

来自专栏技术碎碎念

Mybatis插入数据后返回主键id

19830
来自专栏mathor

SQL注入

 其中,un和pwd都是String类型的变量,这是一个很明显的SQL注入漏洞,假设我令

65160
来自专栏小樱的经验随笔

基于约束的SQL攻击

前言 值得庆幸的是如今开发者在构建网站时,已经开始注重安全问题了。绝大部分开发者都意识到SQL注入漏洞的存在,在本文我想与读者共同去探讨另一种与SQL数据库相...

30690
来自专栏difcareer的技术笔记

C代码 从源代码到可执行文件——编译全过程解析

程序的生命周期从一个高级C语言程序开始,这种形式能够被人读懂,却不能被机器读懂,为了在系统上运行这个程序,该源程序需要被其他程序转化为一系列低级机器语言指令,然...

59950
来自专栏安恒网络空间安全讲武堂

Sqli_labs65关通关详解(下)

less-31 逻辑跟30关一样,只不过 $id = '"' .$id. '"'; $sql="SELECT * FROM users WHERE id=($i...

46180
来自专栏GreenLeaves

oracle10g获取Date类型字段无时分秒解决办法!

一般的数据库中,DATE字段仅仅表示日期,不包括日期信息,而Oracle数据库中的DATE数据类型是包括日期、时间的,对于不同的Oracle jdbc驱动版本,...

21250
来自专栏别先生

|ERROR|ERROR: missing data for column "createtime" (seg3 slice1 192.168.66.23:40001 pid=33370)之mys

引发这个错误,并不是这个字段引起的错误,一般是这个字段临近的字段存在空格或者换行符引发的错误。

7720
来自专栏Python研发

MySQL[一]

1·什么是MySQL丶Oracle丶SQLite丶Access丶MS SQL Server等?

12830
来自专栏FreeBuf

基于约束的SQL攻击

前言 值得庆幸的是如今开发者在构建网站时,已经开始注重安全问题了。绝大部分开发者都意识到SQL注入漏洞的存在,在本文我想与读者共同去探讨另一种与SQL数据库相关...

23250
来自专栏WindCoder

数组版个人通讯录-C语言

25320

扫码关注云+社区

领取腾讯云代金券