在 MySQL 与 PHP 中执行计算

2022-08-30 09:46:53

上下文:

  • 我们有一个PHP / MySQL应用程序。
  • 计算的某些部分是直接在SQL中完成的。例如:过去24小时内创建的所有用户都将通过SQL查询返回( NOW() – 1天)

一位开发人员和我之间正在进行一场辩论,我认为我们应该:

A. 在PHP中保留所有计算/代码/逻辑,并将MySQL视为“哑”信息存储库

他的观点:

B.根据更容易/更快的方式进行混合和匹配。http://www.onextrapixel.com/2010/06/23/mysql-has-functions-part-5-php-vs-mysql-performance/

我正在研究可维护性的观点。他正在研究速度(正如文章所指出的那样,MySQL中的某些操作更快)。


@bob小马@mu@tekretic @OMG驱逐舰@Tudor君士坦丁@tandu @Harley

我同意(很明显)高效的 WHERE 子句属于 SQL 级别。但是,像这样的例子呢:

  1. 使用 NOW() 计算 24 个周期 - SQL 中的 1 天以选择过去 24 小时内创建的所有用户?
  2. 返回所有用户的大写名字和姓氏?
  3. 连接字符串?
  4. (想法,伙计们?

属于 SQL 域的明确示例:

  1. 特定的“位置”选择
  2. 嵌套的 SQL 语句
  3. 订购/排序
  4. 选择非重复项
  5. 计算行/项目

答案 1

我会发挥每个系统的优势。

聚合、联接和过滤逻辑显然属于数据层。它的速度更快,不仅因为大多数数据库引擎都有10多年的优化来做到这一点,而且您可以最大限度地减少在数据库和Web服务器之间移动的数据。

另一方面,我使用过的大多数数据库平台在处理单个值时都具有非常差的功能。像日期格式化和字符串操作这样的东西只是在SQL中很糟糕,你最好在PHP中做这项工作。

基本上,使用每个系统来完成它所要执行的操作。

在可维护性方面,只要发生的事情之间的划分是明确的,将这些划分为逻辑类型应该不会造成太大问题,当然也不足以消除好处。在我看来,代码的清晰度和可维护性更多的是关于一致性,而不是将所有逻辑放在一个地方。


回复:具体示例...

  1. 我知道这不是你所指的,但日期几乎是一个特例。您希望确保系统生成的所有日期都是在 Web 服务器或数据库上创建的。否则,如果数据库服务器和Web服务器配置为不同的时区,则会导致一些阴险的错误(我已经看到这种情况发生了)。例如,假设您有一列,其默认值为 DB 在插入时应用如果要插入记录,则使用PHP中生成的日期(例如,选择在过去一小时内创建的记录),您可能无法获得预期的结果。至于你应该在哪个层上这样做,我更喜欢DB,因为在示例中,它允许你使用列默认值。createdDategetDate()date("Y-m-d", time() - 3600)

  2. 对于大多数应用程序,我会在PHP中执行此操作。将名字和姓氏结合起来听起来很简单,直到你意识到你有时也需要称呼,头衔和中间名首字母。另外,您几乎肯定会遇到这样的情况:您想要用户的名字,姓氏以及组合称呼+名字+姓氏。将它们连接在数据库端意味着您最终会移动更多数据,尽管实际上,这是非常小的。

  3. 取决于。如上所述,如果您想单独使用它们,最好在性能方面将它们单独拉出并在需要时连接。也就是说,除非你处理的数据集很大,否则可能还有其他因素(如你所提到的,可维护性)更有影响力。

一些经验法则:

  • 应在数据库中生成增量 ID。
  • 就个人而言,我喜欢DB应用的默认值。
  • 选择时,任何减少记录数的事情都应该由数据库完成。
  • 通常,最好做一些可以减小数据集数据库端大小的事情(如上面的字符串示例)。
  • 正如你所说;排序、聚合、子查询、联接等应始终是数据库端。
  • 另外,我们还没有谈论它们,但触发器通常是坏的/必要的。

这里有一些核心权衡,平衡实际上取决于您的应用。

有些事情绝对应该 - 每次 - 总是在SQL中完成。排除许多任务的一些例外(如日期的事情)SQL可能非常笨拙,并且可能会让您在偏僻的地方使用逻辑。在代码库中搜索对特定列的引用(例如),很容易错过视图或存储过程中包含的引用。

性能始终是一个考虑因素,但是,根据您的应用程序和具体示例,可能不是一个大问题。你对可维护性的担忧,可能非常有效,我提到的一些性能优势非常小,所以要小心过早的优化。

此外,如果其他系统直接访问数据库(例如,用于报告或导入/导出),您将受益于数据库中的更多逻辑。例如,如果要直接从另一个数据源导入用户,则在 SQL 中实现类似于电子邮件验证函数的可重用功能。

简短的回答:视情况而定。:)


答案 2

我不喜欢重新发明轮子。我也喜欢使用最好的工具来完成需要完成的任务,所以:

  • 当我可以直接从DB获得结果集而无需进一步处理时,我就会这样做 - 您的情况是一个带有简单子句的简单查询。想象一下,当你有1000万用户并且你让他们使用PHP时会发生什么,只需要其中的100个 - 你猜对了 - 你的Web服务器很有可能崩溃WHERE
  • 当您需要同时从2个或更多表中获取数据时,MySQL比PHP好得多。
  • 当您需要计算记录时 - DB非常擅长
  • 我倾向于将应用程序级处理设置为 FK 约束
  • 此外,我倾向于避免存储过程,更喜欢在应用程序级别实现该业务逻辑(当然,除非我们谈论的是巨大的数据集)。

最后,我想说,你的同事在所提出的案例中是对的。


推荐