什么更好?查询文件系统还是查询数据库?

3
我们的文件系统中有大约50万张图片。多个图片属于一个产品,并以ProductID命名。例如,产品ID为10010的有3张图片:10010_1.jpg、10010_2.jpg和10010_3.jpg。为了在照片库中显示这3张图片,当前的经典ASP代码正在查询文件系统。该代码看起来像这样:
Dim objFSO, i
Set objFSO = Server.CreateObject("Scripting.FileSystemObject") 
i=1
While objFSO.FileExists(Server.MapPath(productid & "_" & i & ".jpg")
    ' draw the image
    i = i + 1
WEnd

把图片名称存储在数据库表中,然后运行查询以获取给定产品的可用图像列表,这不是更好的想法吗?我相信从数据库中读取会更好。只是有些犹豫,因为我需要一个拥有50万条记录的大表。哪种方式更有效?

我的表将如下所示:

ID      ProductID   ImageURL
-------------------------------------------
1       10010       10010_1.jpg
2       10010       10010_2.jpg
3       10010       10010_3.jpg
4       10011       10011_1.jpg
. . .

有什么建议吗?我正在使用ASP .NET MVC 3重写网站。在这个平台/框架中,还需要注意哪些额外的事项?


所有这些文件都在同一个目录下吗? - Mike Purcell
在4个目录中。根据图像大小而定。 - Romeo
使用数据库会更好,如果您的数据库有100万条记录,性能不会下降,但是当使用文件系统解决方案时,您的应用程序将会崩溃。 - Saeed-rz
4个回答

3
我认为,你可以实现以下两种解决方案之一:
  1. 混合 - 使用数据库将文件在文件系统中的路径存储起来。

  2. NoSQL - 完全摆脱数据库,使用提供访问文件系统API的NoSQL解决方案。

我曾看到过这两种实现,#1是在#2变得流行之前使用的。尽管我使用#1的时间更长,但我认为对于存储“资产”数据(图像、HTML描述、视频文件),#2是最好的选择。与使用MySQL访问资产数据相比,NoSQL更好的原因是你不需要浪费宝贵的数据库连接来获取文件路径。
另外,还有一个建议:使用产品ID作为父目录分块处理你的目录。考虑以下内容:
# yours
dir1
  ... 125K files
dir2
  ... 125K files

# chunked (parent dirs are product ids)
3
  ... 3 files
4 
  ... 2 files
5 
  ... 3 files

当一个目录下只有少量文件(< 100个)时,使用stat命令查看文件状态信息的速度要比在一个包含数千个文件的目录中快得多。


NoSQL听起来是个不错的想法。我需要做一些研究。 - Romeo
这是一个很好的SO帖子,询问.NET的NoSQL解决方案:http://stackoverflow.com/questions/1777103/what-nosql-solutions-are-out-there-for-net - Mike Purcell

1

在数据库中有五十万条记录并不算太多。

如果您的表正确地建立了索引,那么与文件系统相比,您将获得更好的数据库性能。


0

是的,在数据库中存储文件路径是有意义的,即使存在一些性能损失也会更好。

请注意,将数据存储在磁盘上(文件)和数据库中(文件路径)可能会为应用程序带来新类别的错误,导致数据不一致。在迁移期间要考虑到这一点。

既然问题涉及性能-对于您的数据集进行原型设计和测量,如果性能是一个关注点,则需要考虑以下因素:

  • 您不需要为此构建网站,从磁盘/数据库读取数据的简单控制台应用程序可能已经足够了。
  • 也可以尝试不同的文件布局(例如,在一个目录中存储大量文件可能会减慢文件搜索速度)
  • 确保您知道数据是否将被缓存。如果您的数据库太大无法缓存,那么与适合内存的情况相比,您将得到完全不同的数字。不要忘记,根据服务器配置,一些其他服务也可能竞争使用相同的内存。

图片存储在文件系统中,我不想将它们移动到数据库中。我只想在数据库中存储文件名和路径。 - Romeo
1
是时候睡觉了...重新阅读了你的问题后,我的回答就没有太多意义了...是的,在数据库中存储文件路径是完全有意义的,即使会有一些性能损失(这是极不可能的),但这样做会更好。 - Alexei Levenkov
由于与问题无关,答案已更新。 - Alexei Levenkov

0

一些需要考虑的问题。我假设这是一个 .NET 堆栈,所以:

  1. 数据库空间很昂贵
  2. 从磁盘读取比从关系型数据库读取会更快
  3. 如果所有图像都在数据库中,则在负载平衡环境中会有更多问题
  4. 从数据库中读取大量数据将对其他查询产生负面影响
  5. 无论您的表示层是 MVC、Web 表单还是控制台应用程序,您的问题都在数据库设计中。

我希望在数据库中存储图像的名称和路径,而不是整个图像。并且,我想要运行一个查询数据库的操作来检查图像是否存在,而不是查询文件系统。 - Romeo

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接