如何让func函数按Blog仅调用一次,而非随Post重复执行?
让函数按每个Blog仅调用一次的优化方案
现有Blog和Post两张表,二者为一对多关联(关联关系:Blog.id = Post.b_id)。原查询如下:
SELECT p.*, b.*, func(b.id) AS funcres FROM Blog b, Post p WHERE b.id = p.b_id;
这个查询中func函数的调用次数等于Post表的总记录数——每一条Post记录都会触发一次函数调用。下面提供几种更合理的方案,让func按每个Blog仅调用一次:
方法1:预计算Blog的函数结果再关联
先对Blog表一次性计算所有记录的func结果,再和Post表做关联,这样每个Blog只会触发一次func调用:
SELECT p.*, b.*, blog_func.funcres FROM Blog b JOIN ( SELECT id, func(id) AS funcres FROM Blog ) blog_func ON b.id = blog_func.id JOIN Post p ON b.id = p.b_id;
这种写法逻辑清晰,子查询阶段就完成了所有Blog的func计算,后续关联Post时直接复用结果,完全避免了重复调用。
方法2:使用LATERAL JOIN(部分数据库支持)
如果你的数据库支持LATERAL JOIN(比如PostgreSQL、SQL Server等),可以用这种方式,同样保证每个Blog仅调用一次func:
SELECT p.*, b.*, blog_func.funcres FROM Blog b JOIN LATERAL ( SELECT func(b.id) AS funcres ) blog_func ON true JOIN Post p ON b.id = p.b_id;
LATERAL JOIN会针对每一行Blog执行一次子查询,所以每个Blog只触发一次函数调用,之后关联Post时直接使用已计算好的结果。
关于你当前的写法
你找到的子查询写法确实能实现需求,但逻辑上没必要通过自关联Blog表来获取结果,可读性和直观性不如上面两种方案。如果数据库不支持LATERAL JOIN,这种写法可以作为备选,但优先推荐第一种预计算的方式。
内容的提问来源于stack exchange,提问作者Ilya
相关产品推荐
相关产品推荐

