【发布时间】:2014-03-13 17:35:20
【问题描述】:
数据是财务数据,以存储桶的形式结构化,其中一个存储桶 (Rollup) 可以包含其他数据存储桶。作为示例结构:
Rollup1 | Dept1
Rollup1 | Rollup2 | Dept2
Rollup1 | Rollup2 | Dept3
Rollup1 | Rollup3 | Dept4
Rollup1 | Rollup3 | Rollup4 | Dept5
Rollup1 | Rollup3 | Rollup4 | Dept6
这有 8 列,Rollups 和 Depts 分散在各处(但叶子总是单个 Depts)。大约 10k 行。
查询结果的目标是显示包含所有汇总的单列,具有可变逻辑以正常显示某些汇总,并修改所有其他汇总。
例如,如果我的变量包含“Dept4”,我的结果将是:
Rollup1
Rollup3
NA - Rollup2
NA - Rollup4
在实际场景中,有 3 个变量决定 Rollup 列的显示。
这就是我所拥有的,它应该可以发挥作用,但是性能非常糟糕。 1 Query 最多需要 5 秒,我想改进一下。
SELECT DISTINCT CASE
WHEN "2" NOT IN
(
SELECT "2"
FROM "Finance New"
WHERE (@VAR3 = 'All' OR @VAR3 IN ("2","3","4","5","6","7","8","9"))
AND (@VAR4 = 'All' OR "10" = @VAR4)
AND (@VAR5 = 'All' OR "11" = @VAR5)
)
THEN
'Z N/A - ' || "2"
ELSE
"2"
END AS COL2
FROM "Finance New"
WHERE "5" <> 'All Applicable' AND "1" <> '9999'
AND "2" LIKE '9%'
UNION
SELECT DISTINCT CASE
WHEN "3" NOT IN
(
SELECT "3"
FROM "Finance New"
WHERE (@VAR3 = 'All' OR @VAR3 IN ("2","3","4","5","6","7","8","9"))
AND (@VAR4 = 'All' OR "10" = @VAR4)
AND (@VAR5 = 'All' OR "11" = @VAR5)
)
THEN
'Z N/A - ' || "3"
ELSE
"3"
END AS COL2
FROM "Finance New"
WHERE "5" <> 'All Applicable' AND "1" <> '9999'
AND "3" LIKE '9%'
UNION
Etc, for each of the columns in the Rollup/Dept Tree report.
每个联合查询中的内部选择根据可变条件附加到文本。排序是自动完成的。 UNION (AND "3" LIKE "9%") 之前的最后一行是实际抓取汇总。汇总均以 9 开头。
输入参数被标记为@VARx。
我想知道是否有更有效的方法来执行此操作,假设我无法创建临时表并且无法更改数据的结构。
谢谢!
【问题讨论】:
-
'@COL3'应该是字符串还是参数? -
SQL 中,字符串必须使用单引号
',表/列名必须使用双引号"。 SQLite 接受其他引号以与 MySQL 兼容,但这使得该查询不可读;请修复它。 -
这正是我正在使用的 SQLite 的实现所期望的语法。 '@VARNAME' 是实现对变量的表示。在其他情况下,单引号和双引号的使用如您所述 - 双引号指的是列名和表名,单引号表示字符串。我将把 '@VARNAME' 改为 @VARNAME 并注意这代表一个输入参数。
-
你有索引吗?你能加点吗?列的数据类型是什么?你能改变它们吗?
-
你有哪个 SQLite 版本?你能更新吗?
标签: sqlite performance