PHP解析大文件比从MySQL数据库调用数据更快吗?

3

所以,我有一个MySQL数据库中的数据表,例如:

  • 艺术家姓名
  • 艺术家传记
  • 艺术家年龄

假设有100个艺术家。

因为这些数据很少被修改,我创建了一个接口。当管理员使用内容管理系统修改数据时,系统会查询数据库,并将数据序列化为PHP数组并保存在服务器上的文件中。

每次添加新的艺术家时,该文件都会重新创建,例如一周一次。

在前端页面加载时,页面不是查询数据库,而是包含该文件(使用输出缓冲),并从该对象生成HTML页面布局。

这是一个好主意吗?比让数百个用户每次加载页面时都查询数据库更快吗?

作为此问题的扩展,如果我开始分页数据,例如将MYSQL结果对象限制为10行,那么访问整个表作为PHP数组并将其缩小到10个组 - 根据查询字符串回显相关部分是否会更慢?


只要你生成的平面文件不涉及运行多行PHP代码,它就比查询数据库更快。更快的方法是创建一个HTML文件,您可以在不加载PHP解析器的情况下提供服务。但是需要注意速度方面的一件事:加载页面所花费的80%时间都是客户端时间。确保您的JavaScript和CSS经过优化,避免显示未压缩的图像。 - stevendesu
你尝试过使用Apache Bench测试各种方法的速度吗?我建议你两种方式都设置好并进行测试。也许差异不大,无需担心。如果你以前没有使用过ab,可以参考http://www.petefreitag.com/item/689.cfm。 - JAL
1
每当有人想要存储序列化的东西时,更加关键的问题是:为什么不使用var_export呢?与序列化相比,它可以节省很多开销。在进行了这个转换之后,如果你只需要子集SQL/数据库可能会更快,但你需要整个东西一直处于静态PHP数据结构中,由var_export创建的东西_可能_会胜出,这一点仍然存在争议。 - Wrikken
PHP的序列化还有另一种选择,那就是json_encode。 - JAL
@Wrikken非常好的观点。我忽略了他可能只想要静态数据的子集,这种情况下,尝试读取和解释文件总是比数据库慢(更不用说文件系统的开销了)。 - stevendesu
是的 - 在这种情况下,我只需要子集,所以我认为我会选择MySQL路线。 - Mazatec
7个回答

5

这样可能会变得更慢。将其存储在文件系统中将需要反序列化整个文件,即使您只需要一小部分数据。

永远不要忘记:数据库是快速的!如果不快,那么您需要添加索引 ;)

附注:如果您想提高性能(仅在真正需要时),可以使用APC或者更好的方式是缓存完全生成的页面,以便几乎静态地提供服务。


3
系统向数据库查询数据,并将其序列化为 PHP 数组并保存为服务器上的文件。 如果你要这样做,最好直接缓存结果的 HTML ,并让页面包含它。这样可以避免在每次请求时包含可执行代码、遍历数组和创建 HTML。 甚至可以使用此方法缓存分页 HTML。 关于您的文件方法的可扩展性,将序列化数组加载到内存中,对于每个请求来说都不够高效,与从文件中逐步加载的数据库相比,前者的所有内存使用都会减慢整个服务器的速度。

1

我不确定文件解析和MySQL查询执行的速度差异。由于您的内容在管理员更改列表之前是静态的,因此可以创建HTML页面布局并将其存储为HTML文件,供用户使用。这肯定会减少服务器负载,因为页面不需要任何解析或SQL查询执行。

如果您正在使用分页,则无需从MySQL加载完整结果,可以使用LIMIT关键字限制从MySQL表中获取的结果。


1

我无法给你一个 PHP 特定的答案,但我建议不要序列化数据,因为数据库设计用于处理大量数据。我建议您将数据存储在数据库中,因为您可能希望稍后使用它来生成需要聚合数据的报告。如果没有像 mysql 这样的数据库引擎,这样的练习将是禁止的。

最后关于性能问题,IIS 缓存 HTML 输出,我认为 Apache 也会这样做,尽管我不确定。


1

我认为你应该缓存这些文件,而不是让一个文件被读取。

如果更新频率较低,你可以添加一个例程来重新生成静态文件,每个页面都有一个,比如 artists-1.html(最后插入的10个),artists-2.html(接下来的10个)...

查询是有成本的。过滤文件内容并不一定比查询数据库更快(数据更多,效率更低)。

另外要提到的是,对于数据库来说,100行几乎算不上什么。真的。如果是10,000+,你可能会开始担心性能。100行对于任何现代数据库来说都是小菜一碟。

正如我所说,你可以为每次更新“编译”这些静态文件,因此这将只需要几秒钟或更短的时间,优点是提供直接访问,这是检索信息的最快方式(不讨论内存问题,因为内存甚至更快,但需要更复杂的解决方案)。


0

我认为在只涉及100条记录时,无论哪种方式都没有太大的区别。实际上,你所做的就是缓存一个MySql查询。如果你想让它更快,你可以使用APC将查询缓存在内存中。如果将每个结果页面缓存在单独的内存对象中,则速度会更快。


0

那种速度提升可能很诱人,但我认为它不值得创建和解析PHP文件的努力,甚至可能比简单的数据库查询还要慢。此外,你也会失去很多灵活性(你必须实现任何想要在数据上进行的查询)。减少数据库负载的常见方法是使用像Memcached这样的缓存系统。但当速度真正成为问题时,你所面对的不是数百个用户,而是数以万计的规模,因此在没有必要之前不要进行优化。


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