如何防止select found

编程入门 行业动态 更新时间:2024-10-25 13:29:47
本文介绍了如何防止select found_rows在竞争条件下中断?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧! 问题描述

我必须运行一个具有限制和偏移量的查询,并且还需要总数的结果来建立分页.这是一个具有很多条件和联接的复杂查询,因此我想避免只为获得计数而重复两次查询.

I have to run a query that has a limit and offset and I also need the total number of results to build pagination. It's a complex query with a lot of conditions and joins so I would like to avoid doing the query twice just to get a count.

根据 mysql文档,我可以做这个:

mysql> SELECT SQL_CALC_FOUND_ROWS * FROM tbl_name -> WHERE id > 100 LIMIT 10; mysql> SELECT FOUND_ROWS();

但是当我一次收到成千上万个请求时会发生什么,最终会发生这种情况:

But what happens when i'm getting thousands of requests at a time, eventually there will be an instance where this happens:

mysql> SELECT SQL_CALC_FOUND_ROWS * FROM tbl_name -> WHERE __CONDITION1__ > 100 LIMIT 10; //count from query 1 mysql> SELECT SQL_CALC_FOUND_ROWS * FROM tbl_name -> WHERE __CONDITION2__ LIMIT 10; //count from query 2 mysql> SELECT FOUND_ROWS(); //should be count form query 1 but it's count from query 2 mysql> SELECT FOUND_ROWS(); // count from query 2 but it's always 1

我已将查询封装在单独的事务中,但据我了解不能保证会阻止这种竞争情况.

I've encapsulated the queries in separate transactions, but as far as I understand there's no guarantee it'll prevent this race condition.

所以有两个问题,我能以某种方式强迫我的交易来防止这种竞争状况吗? 如果没有,是否还有另一种方法可以执行而又无需再次查询并获取计数呢?

So there's two questions, can i somehow force my transaction to prevent this race condition? If not, is there another way of doing it without doing the query again and retrieving a count?

推荐答案

涉及事务时存在某些问题,不同的隔离级别会或多或少地阻止它们.我已经在此处中对此进行了描述. 例如,像幻像读取之类的问题可能会影响选择的结果,就像您这样做一样.但是,SQL_CALC_FOUND_ROWS的结果将在查询结束后立即存储,并在同一会话中执行另一个查询后立即丢失.那是重要的部分. SQL_CALC_FOUND_ROWS已会话绑定.无法将另一个会话中另一个查询的结果存储在当前会话中. SQL_CALC_FOUND_ROWS的使用不受竞争条件的约束.是SELECT查询的结果,但不是FOUND_ROWS()的结果.请勿混淆.

There are certain problems when it comes to transactions and different isolation levels prevent more or less of them. I've described this in my answer here. A problem like the phantom read for example, can affect the result of a select like you're doing it, yes. But the result of SQL_CALC_FOUND_ROWS is stored as soon as the query finishes and is lost as soon as you execute another query in the same session. That is the important part. SQL_CALC_FOUND_ROWS is session bound. There is no way, that the result of another query in another session is stored in your current session. The use of SQL_CALC_FOUND_ROWS is not subject to race conditions. The result of the SELECT query, yes, but not the result of FOUND_ROWS(). Don't confuse this.

更多推荐

如何防止select found

本文发布于:2023-10-23 19:48:52,感谢您对本站的认可!
本文链接:https://www.elefans.com/category/jswz/34/1521840.html
版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系,我们将在24小时内删除。
本文标签:如何防止   select

发布评论

评论列表 (有 0 条评论)
草根站长

>www.elefans.com

编程频道|电子爱好者 - 技术资讯及电子产品介绍!