扫一扫
分享文章到微信
扫一扫
关注官方公众号
至顶头条
作者:论坛整理 superhasty 来源:天新网 2008年4月23日
关键字: 数据库 Mssql SQL SQL Server
在本页阅读全文(共4页)
测试3:建立非聚集索引情况下,执行SQL语句
如果将表中同一字段的聚集索引换成非聚集索引,则可以看到如下特点:
3.2 执行高选择性选取
在进行测试前,我们先准备另外一张表和数据。
以下是引用片段: Create Table P_Order ( UserStatus int NOT NULL, MobileNo int NOT NULL, Sid int Not NULL, LastSubTime DateTime ) |
插入数据:
以下是引用片段: Declare @i int Set @i=20000 WHILE @i<30000 BEGIN Insert Into P_Order Select @i % 2,@i,@i-19999,GetUTCDate() set @i=@i+1 END |
可以看到,在执行全表扫描情况下,该表10000条数据总共占用38个内存数据页。
4.1 执行全表选取或者低选择性选取
以下是引用片段: Select * From P_Order A Inner Loop JOIN P_User B ON A.MobileNo=B.MobileNo |
对于此种高选择性选择,默认情况下SQL Server不会执行Loop Join。因此,使用了强制性的联接提示。
在两个表都没有任何索引的情况下,可以看到:
两个表所有的数据页都将被加载到内存。逻辑读取代价高达6万多次——对于P_Order表中的每一条记录,都将在P_User表中进行遍历。
在其中一个表有聚集索引情况下,尽管逻辑读取相比刚才的6万多次已经大大下降,但仍然达到2万次。而且联接的次序对查询性能影响很大。因为其实际执行的是将SQL语句中前面的表作为联接的外部输入,而后面的表作为联接的内部输入。
在两个表都有聚集索引情况下,相比较而言,逻辑读仍然达到数千次(取决于最终输出的数据大小),但相比较已经大大改善。而且表中的数据只有最终需要输出的部分才会被读入内存Buffer中。
4.2 执行高选择性选取
执行如下的SQL语句:
以下是引用片段: Select * From P_Order A Inner merge JOIN P_User B ON A.MobileNo=B.MobileNo Where A.MobileNo=28913 |
在一个表有聚集索引或者非聚集索引情况下,该表将执行Index Seek,另一个表将出现全表扫描。内存数据缓冲区中,将有一张表只读入最终数据所在的数据页、一张表读入全部数据页。逻辑读数取决于表在联接中的秩序、以及无索引表的数据页数。
在两个表都有聚集索引情况下,逻辑读最小,每个表只有2到3次。而且只有实际需要输出的数据才会被读入内存页。两个表都有非聚集索引情况下,消耗的逻辑读和内存资源近似。
如果您非常迫切的想了解IT领域最新产品与技术信息,那么订阅至顶网技术邮件将是您的最佳途径之一。
现场直击|2021世界人工智能大会
直击5G创新地带,就在2021MWC上海
5G已至 转型当时——服务提供商如何把握转型的绝佳时机
寻找自己的Flag
华为开发者大会2020(Cloud)- 科技行者