Dmy*_*sin 5 sql t-sql sql-server dbcc sql-server-2012
我有大约 300 个表,每个表有 5.5kk 行。其中一行使用 nvarchar(128) 作为数据类型 (SQL Server 2012)。
我们决定将其更改为 int 并将 FK 添加到包含所有 nvarchar 的字典表中。
完成所有操作后,我删除了 nvarchar 列,但表的大小保持不变。我使用 DBCC CLEANTABLE 并重建索引以回收可用空间,但表的大小仍然没有改变。
到目前为止,我发现的唯一方法是将所有数据复制到新表中。
问题:我在这里缺少什么?为什么空间仍然被标记为已用而我不能通过收缩或 CREANTABLE 命令释放?
谢谢!
答:看起来答案很简单,由于我缺乏知识,我无法找到它。这里的主要问题是堆碎片。这个查询对我有用:
ALTER TABLE [TABLE_NAME] REBUILD
Run Code Online (Sandbox Code Playgroud)
我不确定这是最好的方法,但至少它是一种有效的方法。
Edited1:抱歉,我想我忘了提及 - 我在 Text 字段上有聚集索引,所以我必须删除索引才能真正删除该字段。现在我没有索引。
编辑2:
旧表:
CREATE TABLE [dbo].[Data_](
[ID] [bigint] PRIMARY KEY IDENTITY(1,1) NOT NULL,
[Text] [nvarchar](128) NOT NULL,
[Category] [tinyint] NOT NULL,
[Country] [nvarchar](2) NOT NULL,
[ImportTimestamp] [date] NOT NULL
)
Run Code Online (Sandbox Code Playgroud)
新表:
CREATE TABLE [dbo].[Data_New](
[ID] [int] PRIMARY KEY IDENTITY(1,1) NOT NULL,
[Category] [tinyint] NOT NULL,
[Country] [nvarchar](2) NOT NULL,
[TextID] [int] NOT NULL)
ALTER TABLE [dbo].[Data_New] WITH CHECK ADD FOREIGN KEY([TextID])
REFERENCES [dbo].[Dictionary] ([Id])
Run Code Online (Sandbox Code Playgroud)
复制脚本:
INSERT INTO Data_New
([Category]
,[Country]
,[TextID])
SELECT
[Category]
,[Country]
,[TextID]
FROM Data_
Run Code Online (Sandbox Code Playgroud)
如果您不关心理解问题而只是想摆脱它,那么重建索引是消除任何浪费的可靠方法。这是因为索引重建会重新构建物理数据结构。旧索引包含的任何内容都不再重要。
与 进行比较时需要权衡CLEANTABLE。如果重建可以满足您的需求,我总是会这样做,因为这是一个完整的解决方案。
当我在这个答案中说“索引”时,我指的是包含您关心的列之一的所有物理结构。这可以是 B 树索引或表所基于的堆。
| 归档时间: |
|
| 查看次数: |
3905 次 |
| 最近记录: |