在SQL Server里禁用聚集索引——真的好么?
有人问了我一个最有意思的问题:“你能禁用聚集索引么?”
对这个问题,我先是吓了一跳,因为我从未想过禁用聚集索引,因为聚集索引代表表数据,对这个最有趣问题,我立即答道:“我认为可以,但是...”
好吧,我们现在来讨论下“但是”。你禁用聚集索引,但我真的不知道SQL Server会如何反应,因此我们来试验下。
(以下代码运行在AdventureWorks2008R2数据库)
-- Let's disable a Clustered Index
ALTER INDEX PK_Person_BusinessEntityID ON Person.Person DISABLE
GO
哈!语句还是可以正常执行的!但是你收到很多不同的外键约束也被禁用的警告。

好,我们已经禁用了表的聚集索引,但我们也有效的禁用了表本身。我们对禁用的聚集索引运行一个简单的SELECT语句。
-- Let's run a SELECT statement against the disabled Clustered Index
SELECT * FROM Person.Person
GO
这下玩完了!!!查询处理器无法生成计划,我们弄坏了我们的SQL语句。

当你开始考虑它的时候,很能想到这是有道理的:我们禁用了聚集索引,也禁用了表本身!但这不应该真的有关系,因为表上有非聚集索引,也可以作为我们获取数据的路径。
我们再想下。我们是否可以通过非聚集索引来访问表数据?理论上是可以的,只要选择的非聚集索引是覆盖非聚集索引。如果你通过从聚集索引的书签查找来请求一些其它列,你还是会有大问题,因为聚集索引已经禁用。因此我们来通过查询sys.index来看下非聚集索引的状态:
SELECT object_id , name ,index_id ,type ,type_desc , is_disabled FROM sys.indexes WHERE object_id=OBJECT_ID('Person.Person')

哇!我们所有的的非聚集索引也被禁用了!现在根本没有方法访问我们的数据了。这是完全有道理的,因为不然的话会引入需要书签查找的巨大问题。现在我们通过禁用聚集索引已经完全把表下线了!
怎么恢复表在线呢?简单:我们需要重建我们的聚集索引:
-- Let's rebuild the Clustered Index
ALTER INDEX PK_Person_BusinessEntityID ON Person.Person REBUILD
GO
很简单,是不是?但当我们再次查询sys.index时,我们会看到我们的非聚集索引“还是禁用的”!

因此我们“也要”重建我们的非聚集索引,让它们恢复在线。
教训:绝不禁用表的聚集索引!
感谢关注!
原文链接:
在SQL Server里禁用聚集索引——真的好么?的更多相关文章
- SQL Server的非聚集索引中会存储NULL吗?
原文:SQL Server的非聚集索引中会存储NULL吗? SQL Server的非聚集索引中会存储NULL吗? 这是个很有意思的问题,下面通过如下的代码,来说明,到底会不会存储NULL. --1.建 ...
- SQL Server里因丢失索引造成的死锁
在今天的文章里我想演示下SQL Server里在表上丢失索引如何引起死锁(deadlock)的.为了准备测试场景,下列代码会创建2个表,然后2个表都插入4条记录. -- Create a table ...
- SQL Server中的聚集索引(clustered index) 和 非聚集索引 (non-clustered index)
本文转载自 http://blog.csdn.net/ak913/article/details/8026743 面试时经常问到的问题: 1. 什么是聚合索引(clustered index) / ...
- 程序员眼中的 SQL Server-非聚集索引能给我们带来什么?
写在前面 最近在做的一个项目,页面访问的时候很慢(大概几秒钟的样子),然后用日志记录的方式,来排查这个问题,最后发现是 Entity Framework 初始化的一个坑(大概要花 6-7 秒),详见: ...
- Entity Framework Code First+SQL Server,改变聚集索引,提高查询性能
.net Entity Framework(调研的是Entity Framework 4.0) code first方式生成数据库时,不能修改数据库表的索引,而SQLServer默认会把数据表的主键设 ...
- SQL Server里在文件组间如何移动数据?
平常我不知道被问了几次这样的问题:“SQL Server里在文件组间如何移动数据?“你意识到这个问题:你只有一个主文件组的默认配置,后来围观了“SQL Server里的文件和文件组”后,你知道,有多 ...
- SQL Server里书签查找的性能伤害
在我的博客上,以前我经常谈到SQL Serverl里的书签查找,还有它们带来的很多问题.在今天的文章里,我想从性能角度进一步谈下书签查找,还有它们如何拉低你整个SQL Server性能. 书签查找—— ...
- SQL Server里的INTERSECT
在今天的文章里,我想讨论下SQL Server里的INTERSECT设置操作.INTERSECT设置操作彼此交叉2个记录集,返回2个集里列值一样的记录.下图演示了这个概念. INTERSECT与INN ...
- SQL Server 重新组织生成索引
标签:SQL SERVER/MSSQL SERVER/数据库/DBA/索引/统计信息 概述 无论何时对基础数据执行插入.更新或删除操作,SQL Server 数据库引擎都会自动维护索引.随着时间的推移 ...
随机推荐
- [转载]sql语句练习50题
Student(Sid,Sname,Sage,Ssex) 学生表 Course(Cid,Cname,Tid) 课程表 SC(Sid,Cid,score) 成绩表 Teacher(Tid,Tname) ...
- DeviceOne接受了DevStore的专访
DevStore隶属深圳尺子科技有限公司,DevStore所有内容(资讯.数据.工具|服务.资源文章.问答……)都贯穿整个项目的生命周期,无论你是设计人员.开发人员.推广人员还是运营人员都可在此找到你 ...
- fsfds
ccc fs -fsd fsdfsfs
- Java中main()的args的知识点浅谈
我们先来了解下Java中main()方法的默认定义格式: public static void main(String[] args){ }1.main方法是程序执行的入口,除了args这个形参变量可 ...
- 邮件开发——base64账号密码转换
package com.hq.base64; import java.io.BufferedReader; import java.io.FileInputStream; import java.io ...
- Java删除数据库中的数据
1:删除数据库中数据表中的数据同样也是一个非常用的技术,使用executeUpdate()方法执行用来做删除SQL的语句可以删除数据库表中的数据 2:本案例使用Statement接口中的execute ...
- (Task)任务异步(TAP)的使用
任务有返回值例子: using System; using System.Collections.Generic; using System.Linq; using System.Text; usin ...
- Ext2.x学习笔记
Ext2.X学习笔记一 一.ExtJS简介 1.1 什么是Ext JS? · Ext JS是一个Ajax框架,可以用来开发富客户端的Ajax应用,是一个用javascript写的,主要用于创建前端用 ...
- 如何使用ITEXTSHARP将HTML代码字符串写进PDF
原文 如何使用ITEXTSHARP将HTML代码字符串写进PDF itextsharp包括一个简单的类,可以用来根据html代码或字符串创建pdf文件.使用此类,你可以使用短短几行代码,就将 HTML ...
- mysql创建数据库指定编码uft8
mysql创建数据库指定编码uft8 CREATE DATABASE IF NOT EXISTS my_db default character set utf8 COLLATE utf8_gener ...