PostgreSQL: Hash Semi Join
explain update test t set crt_time = now() where exists(select 1 from test1 t1 where t1.id = t.id);
-> Update on test t (cost=396607.58..1934979.49 rows=10000070 width=37) -> Hash Semi Join (cost=396607.58..1934979.49 rows=10000070 width=37) Hash Cond: (t.id = t1.id) -> Seq Scan on test t (cost=0.00..580400.00 rows=30000000 width=23) -> Hash (cost=193480.70..193480.70 rows=10000070 width=10) -> Seq Scan on test1 t1 (cost=0.00..193480.70 rows=10000070 width=10) (7 rows)
解释:
Hash Semi join 在左侧和右侧之间执行半连接。右侧只用于确定左侧的哪些行将显示在结果中。使用 HashSemijoin 时,将读取右侧,以形成内存中的散列表,然后将按左侧的每一行探查该表。如果找到匹配项,左侧的行被输出到结果中,匹配过程将重新开始以查找左侧的下一行。必须至少有一个等值连接条件,查询优化程序才会考虑使用 HashSemijoin。
与 NestedLoopsSemijoin 相同,若连接的输入包括来自已被重写为连接的存在限定(IN、SOME、ANY、EXISTS)嵌套查询的表表达式,则可使用 HashSemijoin。如果连接条件包括非等值条件,或不存在合适的索引使得对右侧的索引检索开销足够低,则使用 HashSemijoin 将比使用 NestedLoopsSemijoin 的效果更好。
与 HashJoin 一样,如果没有足够的高速缓存来完成操作,HashSemijoin 可能会恢复为嵌套循环半连接策略。如果是这样,性能计数器将递增。您可以使用 QueryLowMemoryStrategy 数据库属性或连接属性读取此监控器,或者在 Windows 性能监控器的 [查询:或者在 Windows 性能监控器的 [查询:内存不足策略] 计数器中读取此监控器。
HashSemijoin 运算符可以使用的内存量取决于服务器的进程并发水平和活动连接数。
严以律己、宽以待人