sql - Snowflake 查询优化器是否尊重 CTE?
问题描述
如果我编写一个包含 CTE 的 SQL 语句,查询优化器是否总是将这些 CTE 作为离散语句保留以单独优化,或者如果它计算出结果 SQL 将更快地执行,它是否可以将这些 CTE 与整个 SQL 的其他部分合并?
这个问题是由另一个用户提出的问题触发的。他们在 CTE 中使用序列生成器;当 CTE SQL 单独运行时,它总是产生 12 个连续的数字,正如预期的那样。但是,当在 CTE 中作为更大 SQL 语句的一部分运行时,它缺少数字,即它没有产生连续的值。
这是大型数据集的一个已知问题/行为,但由于只有 12 个值,它不应该成为问题 - 但事实表明 CTE 没有按书面方式运行,然后加入了 12 个记录结果集到其他表,但是查询优化器重写了整个查询,并将 CTE 逻辑与 SQL 语句的其他部分合并,因此产生了更大的数据集。
解决方案
Snowflake 没有提供很多关于它如何优化查询的解释。
我可以说,一般来说,有两种处理 CTE 的方法:
- 物化 CTE,使其运行一次,然后读取物化版本。
- 将 CTE 逻辑合并到查询的其余部分并作为查询的一部分进行优化。
我实际上希望 Snowflake两者都做,选择更好的执行计划,因为它是一个从数十年的优化经验中学习的现代数据库。在某些情况下,任何一种方法都可能更好。
综上所述,如果代码返回的数据按照您的描述发生了变化,那么就会出现错误。优化的重点不是改变代码的语义(意义)。关键是返回相同的结果,但使用不同的底层算法。
推荐阅读
- javascript - 如何获取 Rails 表单中文本字段的新值?
- javascript - 以对象的字段作为参数获取 javascript 对象的字段名称
- excel - 下面的 VBA 代码在我的家用笔记本电脑(Excel 2016)上运行,但在我的工作笔记本电脑(Excel 2010)上运行,错误“438”
- javascript - Reactjs 获取 URL 路径名 id
- python - 用于获取可能路径的 MxN 网格(矩阵)问题
- python - 在wxpython中一个接一个地切换工具栏小部件4次的逻辑是什么?
- c# - 创建空的 IQueryable
用于 Linq to SQL 并在稍后连接它 - php - 获取 phpunit 配置文件名 API 函数
- ios - 从 Swift 设置 C 处理程序函数
- python-3.x - Python Multiprocessing 在第一次尝试在连接的设备中执行命令时失败,从第二次尝试开始,所有子进程都通过了