移动数据:html
一、有表分区数据库
二、没有表分区app
我这里只讨论没有表分区的状况函数
例子测试
好比:你有三个文件组,其中一个是主文件组spa
测试脚本:.net
1 USE master 2 GO 3 4 5 IF EXISTS(SELECT * FROM sys.[databases] WHERE [database_id]=DB_ID('Test')) 6 DROP DATABASE [Test] 7 8 --1.建立数据库 9 CREATE DATABASE [Test] 10 GO 11 12 USE [Test] 13 GO 14 15 16 --2.建立文件组 17 ALTER DATABASE [Test] 18 ADD FILEGROUP [FG_Test_Id_01] 19 20 ALTER DATABASE [Test] 21 ADD FILEGROUP [FG_Test_Id_02] 22 23 24 25 --3.建立文件 26 ALTER DATABASE [Test] 27 ADD FILE 28 (NAME = N'FG_TestUnique_Id_01_data',FILENAME = N'E:\FG_TestUnique_Id_01_data.ndf',SIZE = 1MB, FILEGROWTH = 1MB ) 29 TO FILEGROUP [FG_Test_Id_01]; 30 31 ALTER DATABASE [Test] 32 ADD FILE 33 (NAME = N'FG_TestUnique_Id_02_data',FILENAME = N'E:\FG_TestUnique_Id_02_data.ndf',SIZE = 1MB, FILEGROWTH = 1MB ) 34 TO FILEGROUP [FG_Test_Id_02]; 35 36 37 --4.建立表,这个表的数据存放在[FG_Test_Id_01] 文件组上 38 CREATE TABLE aa(id INT ,cname NVARCHAR(4000)) ON [FG_Test_Id_01] 39 GO 40 41 42 --5.插入数据 43 INSERT INTO [dbo].[aa] 44 SELECT 1,REPLICATE('s',3000) 45 GO 500 46 47 48 --6.查询数据 49 SELECT * FROM [dbo].[aa] 50 51 52 --7.建立汇集索引在[FG_Test_Id_02]文件组上 53 CREATE CLUSTERED INDEX PK_ID ON [dbo].[aa]([id]) WITH(ONLINE=ON) ON [FG_Test_Id_02] 54 GO 55 56 57 --8.咱们查看一下文件组的逻辑文件名 58 EXEC [sys].[sp_helpdb] @dbname = TEST -- sysname 59 60 61 62 --9.收缩一下FG_Test_Id_01文件组文件 63 DBCC SHRINKFILE(FG_TestUnique_Id_01_data,1) 64 65 66 --10.你能够选择drop掉汇集索引,也能够选择不drop掉汇集索引 67 DROP INDEX PK_ID ON [dbo].[aa] 68 69 USE master 70 GO 71 DROP DATABASE [Test]
上面的脚本虽然简单,可是隐藏了很是多的知识点code
知识点1:建立了两个文件组,如今数据库有三个文件组,包括主文件组,当你不指定任何参数的时候默认建立出来的数据文件是1MB大小htm
知识点2:插入数据,由于表是建立在[FG_Test_Id_01]文件组上,因此数据都会放在E:\FG_TestUnique_Id_01_data.ndfblog
1 CREATE TABLE aa(id INT ,cname NVARCHAR(4000)) ON [FG_Test_Id_01] 2 GO
知识点3:建立汇集索引,其实这句话里面包含了几个动做,在E:\FG_TestUnique_Id_02_data.ndf文件上分配页面,并把aa表的数据
放进去E:\FG_TestUnique_Id_02_data.ndf文件,其实这里汇集索引成为了移动数据的中介,我在
SQLSERVER汇集索引与非汇集索引的再次研究(上)文章写到:汇集索引叶子节点就是数据,咱们把汇集索引(必定要是汇集索引,非汇集索引不是)
创建在E:\FG_TestUnique_Id_02_data.ndf文件上实际上就是把数据页面和汇集索引页面移动到E:\FG_TestUnique_Id_02_data.ndf文件里
由于SQLSERVER是没有 ALTER TABLE aa(id INT ,cname NVARCHAR(4000)) ON [FG_Test_Id_01] 这种语法上
就是说你一旦建表而且表中已经有数据以后,若是你要移动表数据,只能经过汇集索引这个中介来移动表数据
1 CREATE CLUSTERED INDEX PK_ID ON [dbo].[aa]([id]) WITH(ONLINE=ON) ON [FG_Test_Id_02] 2 GO
从下图能够看出数据都已经移动到E:\FG_TestUnique_Id_02_data.ndf文件上
知识点4:为什麽要加上WITH(ONLINE=ON)??若是你的应用是不能停机的话,加上WITH(ONLINE=ON)就能够在线的建立索引
详情参考:CREATE INDEX (Transact-SQL)
1 CREATE CLUSTERED INDEX PK_ID ON [dbo].[aa]([id]) WITH(ONLINE=ON) ON [FG_Test_Id_02] 2 GO
知识点5:为什麽要收缩[FG_Test_Id_01]文件组文件E:\FG_TestUnique_Id_01_data.ndf
由于数据已经移动到E:\FG_TestUnique_Id_02_data.ndf文件上了,既然已经移到E:\FG_TestUnique_Id_02_data.ndf文件上
为什麽E:\FG_TestUnique_Id_01_data.ndf文件还显示5MB大小??
你们能够看一下这篇文章:汇集索引表插入数据和删除数据的方式是怎样的
我delete了数据,SQLSERVER却没有彻底释放空间,其实这里移动数据到别的文件/文件组至关于delete了数据了
可是SQLSERVER并无释放这些空间,因此我须要收缩一下FG_Test_Id_01文件组文件
1 --9.收缩一下FG_Test_Id_01文件组文件 2 DBCC SHRINKFILE(FG_TestUnique_Id_01_data,1)
知识点6:DBCC SHRINKFILE(FG_TestUnique_Id_01_data,1)
SHRINKFILE的单位是MB,上面的语句就是收缩到1MB大小,其实这里若是E:\FG_TestUnique_Id_01_data.ndf文件有数据的话
而且须要占用2MB大小的空间,那么您使用DBCC SHRINKFILE(FG_TestUnique_Id_01_data,1)这句话只能收缩到2MB大小
并不会收缩到1MB大小的,由于这些数据须要占用空间,你怎麽收缩都收缩不了的,不信的话您们能够测试一下
相关文章:
DBCC SHRINKFILE (Transact-SQL)
user database的initial size和dbcc shrinkfile
总结
虽然移动数据的动做比较简单,可是知识点挺多的,有些人只知道怎麽作,不知道为何我以为这样很差
寻根问底是个人特性o(∩_∩)o 哈哈
注意:移动数据只能一张表一张表的移动,若是表里预先已经有汇集索引,须要先drop掉
移动以前查一下表中的数据在哪一个文件组中
1 USE [Northwind] 2 GO 3 EXEC [sys].[sp_help] @objname = N'[dbo].[Categories]' -- nvarchar(776)
若有不对的地方,欢迎你们拍砖o(∩_∩)o
2014-1-19 补充:
有表分区的方法
大概有三种
先建立新的数据文件,文件组,分区方案,分区函数
例如建立三个新的数据文件和文件组,分区方案和分区函数对于这三个新的数据文件和文件组
旧表:不管已经分区或者尚未分区都适用下面三种方法:
方法一:创建中间表(新表),中间表创建在新的分区方案上,而后用insert into 新表 select * from 旧表的方法,插入完毕以后
drop掉旧表
方法二:创建中间表,中间表创建在新的分区方案上,而后用switch to,由于新分区方案有三个分区
那么,switch to只可以将表的所有数据切换到其中一个分区
USE Sales GO ALTER TABLE 旧表 SWITCH PARTITION 1 TO 新表 PARTITION 1 GO
或者
USE Sales GO ALTER TABLE 旧表 SWITCH PARTITION 1 TO 新表 PARTITION 2 GO
或者
USE Sales GO ALTER TABLE 旧表 SWITCH PARTITION 1 TO 新表 PARTITION 3 GO
上面的三条语句就会把旧表的全部数据移动到新表的某个分区,至于移动到哪一个分区由最后那个数字来指定PARTITION 要移动到的分区的数字
完成后drop掉旧表
方法三:drop掉旧表的汇集索引(若是有),而后在旧表上建立一个汇集索引,建立汇集索引的时候指定新的分区方案
这样就会把表数据移动到新分区方案,即新的数据文件里,这个方法跟没有表分区的数据移动是同样的
参考文章:http://blog.csdn.net/smallfools/article/details/4930810
删除文件和删除文件组
--Transact-SQL USE master; GO ALTER DATABASE AdventureWorks2012 REMOVE FILE test1dat3 ; ALTER DATABASE AdventureWorks2012 REMOVE FILE test1dat4 ; GO --Transact-SQL USE master; GO ALTER DATABASE AdventureWorks2012 REMOVE FILEGROUP Test1FG1 ; GO
移数据
-- 备份数据库 backup database xx to disk =xx DBCC SHRINKFILE(BSDF2017,EMPTYFILE ) ALTER DATABASE AdventureWorks2012 REMOVE FILE BSDF2017 ;