从文件或数据库服务器访问数据是否更快?

问题描述 投票:45回答:11

如果我有一个由文件夹和文件组成的静态数据库,访问和操作会比SQL服务器类型数据库更快,考虑到这将用于CGI脚本吗?

使用文件和文件夹时,有哪些提高性能的技巧?

sql performance cgi flat-file
11个回答
55
投票

我会加入它取决于人群。

这是一个没有通用答案的问题,但在很大程度上依赖于手头的情况。我最近甚至将一些数据从SQL数据库移动到平面文件系统,因为数据库的开销加上一些数据库连接可靠性问题,使用平面文件是更好的选择。

在做出选择时我会问自己的一些问题包括:

  1. 我如何消费数据?例如,我只是按照输入的顺序从开头到结尾读取?或者我会搜索符合多个条件的行?
  2. 在一个程序执行期间,我多久会访问一次数据?我会去一次用Salinger作为作者获得所有书籍,还是会多次去找几位不同的作者?我会针对几个不同的标准不止一次?
  3. 我将如何添加数据?我可以直接添加一行,这对我的检索是否完美,还是需要使用?
  4. 代码在六个月内看起来有多合理?我强调这一点是因为我认为这在设计事物时经常被遗忘(不仅仅是代码,这个爱好马实际上来自我作为海军机械师诅咒机械工程师的日子)。在六个月内,当我必须维护你的代码时(或者你在另一个项目之后你做了),哪种存储和检索数据的方式会更有意义。如果从平面文件转到数据库导致效率提高1%,但是当你必须更新代码时,需要花费一周的时间来解决问题,你真的改进了一些东西。

0
投票

我会给你一个其他人给你的答案,这取决于你

在具有返回数据的单个服务器(仅限READ)的简单方案中,Yes文件系统将非常好且易于管理。

但是,当你有多个服务器时,你将不得不管理分布式文件系统,如glusterfsceph等。

数据库是一个管理所有它的工具,分布式文件系统,压缩,读/写,锁等。

希望这很有帮助。


0
投票

像其他人说的那样DB是一个工具,它会产生一些开销,但是如果你的数据是静态的并且它是只读数据从文件读取目录会更快:这里有一些我已经完成的测试:我有一些文件.csv文件的名称在数据库中,我将列索引为“日期”,以便在数据库中查找相同的记录。每天有30K-50K记录/行和100列不同类型的数据(90%浮点数)。

数据库信息:PostgreSQL 11.5,16GB的RAM

  Table:
    335,162,867 records
    Table size: 110GB
    Index size: 7GB
    Total size: 117GB
  Files:
    Number of files: 8033
    Total Files size: 158GB
    Number of records/lines per file/date: 30K - 50K

从文件中读取随机日期(1986-2019)的数据总是比在PostgreSQL中读取同一日期的数据快4-5倍


18
投票

取决于您的信息是什么以及您的访问模式和规模。关系数据库的两个最大好处是:

  1. 缓存。除非你非常聪明,否则你不能写一个像DB服务器那样好的缓存
  2. 优化。

但是,对于某些专门的应用程序,与文件+文件夹数据存储相比,这两种好处都没有表现出来 - 因此答案是响亮的“依赖”。

至于文件/文件夹,技巧是:

  • 缓存频繁请求的文件的内容
  • 拥有小目录(深度嵌套的小目录中的文件比在更平坦的结构中访问要快得多,因为读取大目录的内容需要时间)。
  • 还有其他更高级的优化(跨磁盘切片,放置在磁盘或不同分区中的不同位置等等) - 但如果您需要THAT级别,那么最好先使用数据库。

16
投票

作为一般规则,数据库比文件慢。

如果您需要索引文件,那么如果您正确执行,自定义索引结构上的硬编码访问路径将始终具有更快的可能性。

但是,在基于文件的解决方案上选择数据库时,“性能”不是目标。

您应该问问自己,您的系统是否需要数据库提供的任何好处。如果是这样,那么小的性能开销是完全可以接受的。

所以:

  1. 您需要处理多个用户和并发更新吗? (好吧;你确实说它是静态的。)
  2. 您是否需要灵活性以便从各种角度轻松查询数据?
  3. 您是否拥有多个用户,并且可以从使用现有安全模型中获益?

基本上,问题更多的是更容易开发。两者之间的性能差异不值得浪费开发时间。


8
投票

根据我的一点经验,与本地文件系统相比,基于服务器的数据库(甚至是在本地机器上提供的数据库)往往具有非常慢的吞吐量。然而,这取决于某些事情,其中​​之一是渐近的复杂性。比较扫描大文件列表与使用数据库和索引来查找项目,数据库获胜。

我的一点经验是使用PostgreSQL。我有一张300万行的表,我只更新了8,000条记录。花了8秒钟。

至于引用“过早的优化是所有邪恶的根源。”,我会带着一丝盐。如果使用数据库编写应用程序,然后发现它很慢,则可能需要花费大量时间才能切换到基于文件系统的方法或其他方法(例如SQLite)。我想说你最好的办法就是创建一个非常简单的工作负载原型,并用两种方法进行测试。我相信知道在这种情况下哪个更快是很重要的。


4
投票

正如其他人所指出的那样:这取决于!

如果您确实需要找出哪个更适合您的目的,您可能希望生成一些样本数据以每种格式存储,然后运行一些基准测试。 Benchmark.pm模块附带了Perl,并且可以很简单地与这样的事情进行并排比较:

use Benchmark qw(:all) ;

my $count = 1000;  # Some large-ish number of trials is recommended.

cmpthese($count, {
    'File System' => sub { ...your filesystem code... },
    'Database'    => sub { ...your database code... }
});

您可以输入perldoc Benchmark以获得更完整的文档。


3
投票

如果站点结构合适,在图像方面使用文件而不是db非常有用。创建表示匹配数据的文件夹并将图像放入其中。例如,您有一个文章站点,您将文章存储在db中。您不必将映像路径放在db上,使用主键(如1,2,3 ..)命名文件夹,并将图像放入其中。电子书,音乐文件,视频,这种方法可用于所有媒体文件。如果您不搜索某些内容,则相同的逻辑适用于xml文件。


1
投票

这取决于数据的配置文件以及您将用于访问它的逻辑。如果您只需要保存并获取命名节点,那么基于文件系统的数据库可能更快,更高效。 (你也可以看看Berkeley DB。)如果你需要进行基于索引的搜索,特别是如果你需要基于密钥加入不同的数据集,那么SQL数据库是你最好的选择。

我会选择最适合您应用的解决方案。


1
投票

正如其他人所说,这取决于:数据的大小和性质以及您计划在其上运行的操作。

特别是对于CGI脚本,您将在每个页面视图上连接到数据库服务器时遇到性能损失。但是,如果您创建一个天真的基于文件的方法,您可以轻松地创建更糟糕的性能问题;-)

除了Berkeley DB File解决方案,您还可以考虑使用SQLite。这将为存储在本地文件中的数据库创建一个SQL接口。您可以使用DBI和SQL访问它,但没有服务器,配置或网络协议。如果将来需要数据库服务器,这可以允许更容易的迁移(例如:如果您决定拥有多个前端服务器,但需要共享状态)。

在不知道任何细节的情况下,我建议使用SQLite / DBI解决方案,然后查看性能。这将提供灵活性,具有相当简单的启动和良好的性能。


1
投票

要快速访问文件,根据您的操作,mmap非常方便。我刚刚在Effective Perl博客上写了这篇关于Memory-map files instead of slurping them的文章。

但是,我希望数据库服务器更快。当我们不知道你在做什么,你需要访问什么类型的数据等等时,很难说你会更快。

© www.soinside.com 2019 - 2024. All rights reserved.