Tsql 如何在T-SQL中将filestream中的varbinary(max)转换为实际的varbinary(max)
我有一个数据库,它被设置为在varbinary(max)字段上对音频文件使用blob FileStream。它的大小在80GB以上,我面临性能问题 环顾四周后,我发现我的平均斑点大小约为180k。由于根据文件流应该用于1MB以上的对象,我正在重新评估如何存储这些blob。MSDN还指出,“对于较小的对象,在数据库中存储varbinary(max)blob通常可以提供更好的流性能。”因此,我正在考虑从使用filestream的varbinary(max)改为仅使用varbinary(max)字段Tsql 如何在T-SQL中将filestream中的varbinary(max)转换为实际的varbinary(max),tsql,blob,filestream,Tsql,Blob,Filestream,我有一个数据库,它被设置为在varbinary(max)字段上对音频文件使用blob FileStream。它的大小在80GB以上,我面临性能问题 环顾四周后,我发现我的平均斑点大小约为180k。由于根据文件流应该用于1MB以上的对象,我正在重新评估如何存储这些blob。MSDN还指出,“对于较小的对象,在数据库中存储varbinary(max)blob通常可以提供更好的流性能。”因此,我正在考虑从使用filestream的varbinary(max)改为仅使用varbinary(max)字段
所以我的问题是,有没有一种很好的方法可以使用sql脚本将每个filestream blob从filestream移动到实际的varbinary字段本身?另一种方法,我在决定询问之前一直在研究,就是让c#app查询数据库中的blob,并将每个blob写入文件系统。然后手动从数据库中删除filestream内容。然后让c#应用程序从文件系统中读取blob并写回数据库。我认为必须有一种更简单的方法。假设源表如下所示:
CREATE TABLE audioFiles
(
AudioID INT IDENTITY NOT NULL PRIMARY KEY,
[Name] VARCHAR(50) NOT NULL,
[AudioData] VARBINARY(MAX) FILESTREAM NULL,
RowGuid UNIQUEIDENTIFIER NOT NULL ROWGUIDCOL UNIQUE DEFAULT(NEWID())
)
然后您可以创建第二个表:
CREATE TABLE audioBlobs
(
AudioID INT IDENTITY NOT NULL PRIMARY KEY,
[Name] VARCHAR(50) NOT NULL,
[AudioData] VARBINARY(MAX) NULL,
RowGuid UNIQUEIDENTIFIER NOT NULL ROWGUIDCOL UNIQUE DEFAULT(NEWID())
)
GO
(请注意,第二个表中的AudioData
列中缺少FILESTREAM…导致二进制数据与记录的其余部分一起存储在页面上,而不是存储在单独的FILESTREAM文件组中。)
然后,您可以将数据从一个表插入到另一个表:
SET IDENTITY_INSERT audioBlobs ON
INSERT INTO audioBlobs (AudioID, Name, AudioData, RowGuid)
SELECT AudioID, Name, AudioData, RowGuid FROM audioFiles
SET IDENTITY_INSERT audioBlobs OFF
完成后,可以删除原始表,并将新表重命名为原始表的名称:
DROP TABLE audioFiles
GO
EXECUTE sp_rename N'dbo.audioBlobs', N'audioFiles', 'OBJECT'
GO
或者,您可以在原始表中的FILESTREAM
列旁边创建第二个VARBINARY(MAX)
列,只需使用旧列的数据更新新列的值。请注意,无论采用哪种方式,您的总磁盘空间使用量都将增加一倍以上——将实际音频数据的空间增加一倍,将其从FILESTREAM文件组迁移到主文件组(或主数据文件所在的任何位置),加上事务日志中的大量空间。NEWID()不适合索引。最好改用NEWSEQUENTIALID()。