c# - 提高将数百万张图片存储到数据库中的性能

标签 c# sql-server

我有数百万张图片(每张图片大约 7Kb)位于文件夹 temp 中(在 Windows Server 2012 下),我想将它们存储在 SQL Server 数据库中。

目前我正在做的是:

  • 使用搜索文件:foreach(var file in directory.EnumerateFiles())

  • 将每个文件作为二进制数据读取:byte[] data = System.IO.File.ReadAllBytes("C:\\temp\\"+ file.Name);

  • 使用 SQLCommand 保存每个二进制数据:

    using (SqlCommand savecmd = new SqlCommand("UPDATE myTable set downloaded=1,imagecontent=@imagebinary,insertdate='" + DateTime.Now.ToShortDateString() + "' where imagename='" + file.Name.Replace(".jpg", "") + "'", connection))
    {
        savecmd.Parameters.Add("@imagebinary", SqlDbType.VarBinary, -1).Value = data;
        savecmd.ExecuteNonQuery();
    }
    
  • 插入成功的每张图片都从临时文件夹中删除

这种获取文件并将其存储到数据库中的方式不会花费很多时间,因为 myTableimagename 上有一个聚集索引。 但是,当我们谈论数百万个文件时,完成整个操作需要花费大量时间。

有没有办法改进这种工作方式?例如,不是一个文件一个文件地存储,而是十个十个或一千个存储?还是使用线程?对于此类问题,最好的建议是什么?

最佳答案

您应该考虑通过标识符来索引您的图像存储,而不是您用于图像名称“name.jpg”的大 nvarchar() 字段。 通过索引 ID 搜索要快得多。 所以我建议将您的表格分成两个表格。

第一个持有主唯一 ID(索引)和 ImageBinary。

第二个表包含外键 ID 引用、insertdate、下载、图像名称(PK,如果需要和索引)。

通过集成 View 或存储过程,您仍然可以通过对数据库的单个调用来插入/更新,但只需直接在第一个表上按 ID 查找图片即可读取条目。

要知道调用哪个 ID,您可以将 ID 缓存在内存中(并在启动时从表 2 加载它们)。

这应该加快图片的阅读。

如果您的主要问题是批量插入和更新所有图片,您应该考虑使用用户定义的表类型并将数据批量合并到数据库中 https://msdn.microsoft.com/en-us/library/bb675163(v=vs.110).aspx

如果您可以将逻辑切换为仅插入图片而不是更新,则可以使用 .net 类“SqlBulkCopy”来固定内容。

希望对您有所帮助, 问候

关于c# - 提高将数百万张图片存储到数据库中的性能,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/41018421/

相关文章:

c# - 如何在 .NET 中平衡读写器线程

c# - 无法使用 Linq 访问特定的 XML 文件 block

c# - SignalR:通过代理服务器建立隧道失败

sql - 如何用另外两个表的数据填充一个新表?

c# - 在 .NET 2.0 中序列化私有(private)支持数据成员?

c# - WCF 实例管理

php - 学说 2 : DBAL connection to Sql-Server

MySQL:SQL Server HierarchyId 数据类型的替代解决方案

sql - 如何向表中插入N行默认值

SQL 服务器 : change column to not null in a very large table