【发布时间】:2021-12-18 07:22:47
【问题描述】:
除了直接匹配查询的空白规范化哈希之类的东西之外,还有什么可能是一种有用(但不一定完美)的方式来以部分方式处理查询缓存?例如,让我们以以下基本情况为例:
SELECT
Product, # VARCHAR
Revenue # DOUBLE
FROM
Sales
WHERE
Country='US'
这可能被用作“基础缓存”,可以在其上执行进一步的查询以潜在地提高性能:
SELECT
Product, # VARCHAR
Revenue # DOUBLE
FROM
Sales
WHERE
Country='US' AND State='CA'
因此,假设from 表中的数据没有变化,以下可能作为确定缓存的起点:
- fields: [field:type, ...] // 可以少但不能多
- 来自:表的哈希+连接
- filters: [filter1, filter2, ...] // 可以少但不能多
- 聚合:[agg1, agg2, ...] // 可以少但不能多
- have: [have1, having2, ...] // 可以少但不能多
- order+limit+offset if limited result-set // 可以少但不能多
但是,当我们考虑类似以下情况时,这变得非常棘手:
SELECT
ProductGroup AS Product, # Would produce a Product:VARCHAR hash
Revenue
FROM
Sales
WHERE
Country='US'
对于如何实现部分查询缓存来说,一个现实的起点可能是什么。
用例: 编写 SQL 以查询非 DBMS 管理的源中的数据,例如 CSV 文件,这需要大约 20 秒来发出任何查询,并且我们无法在文件。 https://en.wikipedia.org/wiki/SQL/MED 或类似 Spark。
【问题讨论】:
-
您是否在使用任何现实世界的 DBMS(您忘记标记),这是否应该解决现实世界的性能问题?那么您可能只想在
(country)和(country, state)上创建索引(或者甚至包括(country, product, revenue)和(country, state, product, revenue)之类的投影列(或者也包括productgroup或者为此设置一组额外的索引))并完成。 -
@stickybit 不是真的,它更多的是用于查询非托管源,例如 CSV/Parquet/等。来自数据库的文件(类似于联合数据访问,其中查询需要很长时间并且没有索引选项)。
-
好的。但是为什么不能创建索引而是缓存呢?
-
@stickybit 缓存是应用层。即,我们远程存储缓存数据,因此我们甚至根本不必点击文件。
-
正如我想象的那样,您正在编程所说的应用层?那你也可以在那里实现(覆盖)索引?
标签: sql algorithm caching query-cache