在同一会话中运行的两个连续SELECT查询何时会产生不同的结果



我得到了一个赋值,用来查找两个连续的select查询产生不同结果的情况
我的想法是,如果我们首先运行第一个查询,然后在并行会话中修改一些记录,然后运行第二个查询,结果显然会有所不同
我很好奇除了上述情况之外,是否还有其他情况。

您描述的场景肯定会起作用,但请注意,您必须提交这些更改(不确定是否隐含,但明确可能是个好主意(。

另一个可能是也可能不是有效解决方案的想法是,绕过排序。例如,考虑像SELECT num_col FROM my_table这样的查询。由于没有order by子句,数据库可以自由地以其选择的任何方式返回行。在两个查询之间在num_col上创建索引可能会使数据库更喜欢从中查询数据(全索引扫描与全表扫描(,并且在有索引和没有索引的情况下,很可能会以不同的顺序获得结果。

EDIT:
另一个想法可能是,如果您查询当前时间(例如,PosgreSQL中的SELECT CURRENT_TIMESTAMP,其他RDBMS可能具有略微不同的语法(-数据库中没有数据更改,但随着时间的推移,对同一查询的连续调用将返回不同的结果。

没有必要假设底层数据发生了更改。

最简单的解决方案是使用volatile函数。例如,当在不同的时间运行时,这可能会返回不同的结果——即使底层数据没有更改:

select t.*
from t
where created_at < current_timestamp - interval '1 year';

或者:

select t.*
from t
order by random()
fetch first 100 rows only;

实际上,一个简单的查询是:

select random()

也满足了要求,而实际上不需要涉及任何表。

正如您所说,如果两个选择之间的数据发生了变化,那么同一个连续的两个选择只会产生不同的结果。

您也可以在数据发生更改的事务中进行选择,然后回滚到相同的选择并获得不同的结果,但这再次意味着基础数据发生了更改。

如果设置了"无锁定",则可以查询相同的数据两次,结果不同,例如,如果在您选择的某个期间运行了大型更新。这是一个边缘案例,但它是可能发生的。

Brent Ozark对";无锁定";问题https://www.brentozar.com/archive/2019/08/but-nolock-is-okay-when-the-data-isnt-changing-right/

最新更新