现在我们有一个数据库表(SQL Server 2008 R2),它在图像类型列中存储上传的文件(PDF,DOC,TXT等)。用户从ASP.NET应用程序上载此文件。我的项目是要掌握这张桌子的大小,我一路上想出了几个问题。
在数据库方面,我发现图像列类型据说有些折旧?我可以获得切换到varbinary(max)的任何好处,或者我应该说varbinary(5767168),因为这是我的文件大小上限,或者我也可以让它保留为图像类型,只要空间效率是关注?
在应用程序端,我想压缩字节数组。微软内置的GZip有时会使文件更大而不是更小。我切换到SharpZipLib,这要好得多,但我偶尔会遇到同样的问题。在我大规模实施之前,有没有办法找出平均文件压缩节省?我很难找到他们使用的基础算法。
是否值得编写我自己的霍夫曼代码算法,或者在有时会出现比原始文件更大的压缩文件时会出现同样的问题?
作为参考,如果重要,这是我的应用程序中的代码:
using ICSharpCode.SharpZipLib.GZip;
private static byte[] Compress(byte[] data)
{
MemoryStream output = new MemoryStream();
using (GZipOutputStream gzip = new GZipOutputStream(output))
{
gzip.IsStreamOwner = false;
gzip.Write(data, 0, data.Length);
gzip.Close();
}
return output.ToArray();
}
private static byte[] Decompress(byte[] data)
{
MemoryStream output = new MemoryStream();
MemoryStream input = new MemoryStream();
input.Write(data, 0, data.Length);
input.Position = 0;
using (GZipInputStream gzip = new GZipInputStream(input))
{
byte[] buff = new byte[64];
int read = gzip.Read(buff, 0, buff.Length);
while (read > 0)
{
output.Write(buff, 0, read);
read = gzip.Read(buff, 0, buff.Length);
}
gzip.Close();
}
return output.ToArray();
}
提前感谢您的帮助。 :)
答案 0 :(得分:3)
这不是一个字节数组,那是一个BLOB。 10年前,您将使用IMAGE数据类型。
这些天,使用VARBINARY(MAX)效率更高 我真的建议人们使用FILESTREAM for VarBinary(Max),因为它可以很容易地备份数据库(没有blob)。
请记住,使用原生格式(无压缩)将允许全文搜索..如果您考虑它,这是非常不可思议的。你必须从Adobe安装一些iFilter才能在PDF中搜索..但它是一个杀手级的功能,没有它我就活不下去。
答案 1 :(得分:1)
我讨厌成为一个混蛋并回答我自己的问题,但我认为我会将我的发现总结为一个完整的答案,以便其他任何希望在数据库中空间有效地存储文件/图像数据的人:
*使用varbinary(MAX)与Image?
使用varbinary(MAX)的原因很多,但其中最重要的是不推荐使用Image,而在将来的SQL版本中,它将被完全删除。没有开始任何新的项目只是将未来的问题扼杀在萌芽状态。
根据此问题中的信息:SQL Server table structure for storing a large number of images,varbinary(MAX)可以在其上使用更多操作。
Varbinary(MAX)很容易通过使用SQL参数从.NET应用程序流式传输。负值是'MAX'长度。像这样:
SQLCommand1.Parameters.Add("@binaryValue", SqlDbType.VarBinary, -1).Value = compressedBytes;
*使用什么压缩算法?
我真的不太接近这个问题的正确答案。我使用了ICSharpCode.SharpZipLib.Gzip,发现它比内置的压缩函数具有更好的性能,只需在一堆东西上运行并比较它。
我的结果:
我将文件总大小减少了大约20%。不幸的是,我所拥有的很多文件都是不能很好地压缩的PDF文件,但仍有一些好处。对于已经压缩的文件类型,显然没有太多运气。