数据库索引知识汇总

外键约束:

外键约束为了保证主、子表数据的完整性,在子表进行增、删、改等操作的时候,会同时校验主表的数据是否完整。在这个过程中,会对主表加锁进行查询,这时主表的关联字段一定是主键或者唯一键,它的校验速度非常快,可能不会有太大的问题(在某些情况下,比如子表是日志表或者历史表,对于数据完整性并没有要求,此时请不要在上面加外键约束,因为这只会给系统带来额外的消耗

为外键添加索引的必要性:

在数据库中,当对父表进行更新的时候,如果在子表中的外键没有使用索引,则在更新的过程中整个子表将被锁定,而往往实际上并不需要锁定整个子表,而仅仅需要锁定子表中的几条记录。这样就会大大影响数据库访问的并发性,甚至有可能造成死锁的情况。

除了锁表的问题之外,一个没有使用索引的外键在下面两种情况下表现的也十分糟糕:

  • 当使用ON DELETE CASCADE删除父表中的记录时,如果在子表中的外键没有使用索引则当执行该操作时会对子表进行全表的扫描,而事实上这个全表的扫描是不需要的。更坏的情况是,如果删除多个父表中的记录,每删除一条记录则会进行一次全表扫描,可想而知,对于性能的影响是多么的大!
  • 如果子表数据量非常大,对子表进行全表扫描,开销也会剧增
  • 对于父表和子表的连接查询,情况也是类似的。当进行这种连接查询时,如果不对外键使用索引则会发现查询的速度大大降低

这下你一定明白了为什么需要在外键上使用索引的重要意义了,不过你还是坚持不想使用索引的话,也可以,不过必须保证下面三种情况同时满足:

  1. 不从父表中删除记录
  2. 不更新父表中的主键的值
  3. 一般不进行父表和子表的连接查询

如果你觉得你可以满足上面的全部三个条件,那么你可以不必为外键添加索引。

不过一般来讲,上面的三种情况很难满足,而如果你没有使用索引的话,那么你将为此付出很大的代价的!

本人也看到有些系统中,在同一个外键列上建立多个索引,这样做的动机不太明白,望高手解答...(如下图对OrderId字段建立了2个同样的索引)

 

 其他索引知识总结:

1、表的主键、外键必须有索引;
2、数据量超过300的表应该有索引;
3、经常与其他表进行连接的表,在连接字段上应该建立索引;
4、经常出现在Where子句中的字段,特别是大表的字段,应该建立索引;
5、索引应该建在选择性高的字段上;
6、索引应该建在小字段上,对于大的文本字段甚至超长字段,不要建索引;
7、复合索引的建立需要进行仔细分析;尽量考虑用单字段索引代替:
A、正确选择复合索引中的主列字段,一般是选择性较好的字段;
B、复合索引的几个字段是否经常同时以AND方式出现在Where子句中?单字段查询是否极少甚至没有?如果是,则可以建立复合索引;否则考虑单字段索引;
C、如果复合索引中包含的字段经常单独出现在Where子句中,则分解为多个单字段索引;
D、如果复合索引所包含的字段超过3个,那么仔细考虑其必要性,考虑减少复合的字段;
E、如果既有单字段索引,又有这几个字段上的复合索引,一般可以删除复合索引;
8、频繁进行数据操作的表,不要建立太多的索引;
9、删除无用的索引,避免对执行计划造成负面影响;
以上是一些普遍的建立索引时的判断依据。一言以蔽之,索引的建立必须慎重,对每个索引的必要性都应该经过仔细分析,要有建立的依据。因为太多的索引与不充分、不正确的索引对性能都毫无益处:在表上建立的每个索引都会增加存储开销,索引对于插入、删除、更新操作也会增加处理上的开销。另外,过多的复合索引,在有单字段索引的情况下,一般都是没有存在价值的;相反,还会降低数据增加删除时的性能,特别是对频繁更新的表来说,负面影响更大。

原文地址:https://www.cnblogs.com/gougou1981/p/9928111.html