php - 如何在mysql中根据条件增加行object_id?

标签 php mysql laravel laravel-5

这是示例表:

id | object_class | object_id | name     |
1  | 1            | 1         | potato   |
2  | 1            | 2         | tomato   |
3  | 2            | 1         | wheel    |
4  | 2            | 2         | seat     |

id 自动递增。例如,我想在 object_class 等于 1 时添加行。如何告诉 mysql 在创建新行时,检查对象类中的 object_id,找到最大的一个并使用 object_id+1 创建行?如果 object_class 不存在,则创建 object_id 从 1 开始的新行?所以它补充道:

5 | 1             | 3         | foo     | (for existing)
6 | 3             | 1         | bar     | (for new object_class)

我确实明白我可以以某种方式(如果上述不可能,请解释用很少的查询来执行此操作的最佳优化方法)获取某些 object_class 的 object_id,然后找到最大的一个。之后,使用手动计算的 object_id 创建新行。但这似乎还有很多工作要做。

我想指出,我对 mysql 表优化了解不多。

另外,我使用 laravel 5 框架。

编辑:
刚刚注意到 laravel 有 Aggregate MAX http://laravel.com/docs/5.0/queries 获取最大值然后使用 max+1 创建新行是个好方法吗?

最佳答案

有四种方法可以实现此目的。

  1. 在您的 php 代码中执行所有操作。添加行,查询数据库以获取最大值。创造新记录。所有这些都是在 php 中完成的,并将 autocommit 设置为 false。如果出现问题,您希望能够回滚。要么一切按计划进行,两行按应有的方式插入,要么什么都不插入。
  2. 这与上面的相同。所有 php,但不是在数据库中搜索最大值,而是保留缓存。步骤是这样的:插入行,在缓存中搜索需要的内容,插入第二行,更新缓存。这样会更快,但是很麻烦,因为你必须考虑内存问题。是一些简单的数据结构,还是一些提供这种功能的框架?这些从一开始就很难决定。
  3. 创建一个ON INSERT运行的过程。当您插入行时,该触发器将被激活,并且它将运行您的 SQL 代码。该过程将检查最大值,然后插入新行。
  4. 与 2 相同,但是 run 你可以通过 php 运行你的程序,而不是通过触发器。

我完全支持情况 1 和 2。我倾向于尽可能避免过程和触发器。我不希望我的业务逻辑到处都是。我尝试将所有内容保留在代码中,因为它更易于维护且更易于调试。日志记录也更容易。代码库的新手可以轻松地遵循这些步骤。当然这是我的做法,不一定是正确的方法。在某些情况下,通过代码甚至通过触发器调用的过程可能非常有效,但在您的情况下我没有看到这一点。

在 1 和 2 之间做出选择,这很棘手。这取决于您的应用程序以及您想要实现的目标。 1 很简单,如果速度很慢,您可以尝试通过索引进行优化。如果这有效,那就这样做吧。就简单多了。如果没有,那么您必须考虑情况 2。为您需要的值保留缓存,而不是查询数据库。在启动时,您初始化缓存(这在启动时完成一次,所以即使有点慢,也只是一次)。然后保持缓存最新。如果简单和定制的东西可以,那就很好。如果没有,那么您就开始寻找一些处理此类内容的框架。

这是我的两分钱。我希望这可以帮到你。玩得开心

@zerkms 提供了一些非常有用的见解。你总是会遇到并发问题。所以基本上我知道解决这个问题的两种方法。

  1. 进行事务(所有三个步骤)时完全锁定表(悲观锁定)。当一笔交易发生时,其他交易不能做同样的事情,否则它会搞乱你所追求的最大值的查询。不建议这样做,特别是当应用程序打算提供一些流量时。
  2. 将所需的值保留在同步结构中。检查案例 2。建议这样做。这样,瓶颈只会发生在快速查找时,而不会发生在完整的数据库事务中。

关于php - 如何在mysql中根据条件增加行object_id?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/29018607/

相关文章:

javascript - 通过 Laravel blade 将数据传递给 React 组件

php - 如何使用 PHP Laravel 从 Outlook API 下载附件?

javascript - 如何使用 ID 循环 JavaScript 函数?

php - 网格不显示在自定义 magento 模块中

mysql - 如何在 mysql 中实现双数据类型的相等/近似条件?

php - WordPress网站在专用服务器上运行极其缓慢

PHP: undefined offset :0,但不是 dd()

PHP-MYSQLI : My login scripts logs direct users into the same page

php - 基于换行符将文本存储在MySQL数据库的不同行中

php - CURL PHP 不适用于 WAMP 和 XAMPP