直接case when 聚合和先聚合后case when在duckdb150和sqlite3.52的性能比较

同样对10000000行的内存表执行2个值分别和7个值和11个值的复合分组聚合。

sql 复制代码
C:\d>duckdb150
DuckDB v1.5.0 (Variegata)
Enter ".help" for usage hints.
memory D .timer on
memory D create table t as select i%2 a, i%7 b,i%11 c from range(1,10000000)t(i);
Run Time (s): real 0.288 user 0.234375 sys 0.046875
memory D select a,
         count(case b when 0 then 1 end)b0 ,
         count(case b when 1 then 1 end)b1 ,
         count(case b when 2 then 1 end)b2 ,
         count(case b when 3 then 1 end)b3 ,
         count(case b when 4 then 1 end)b4 ,
         count(case b when 5 then 1 end)b5 ,
         count(case b when 6 then 1 end)b5
         from t group by a;
┌───────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┐
│   a   │   b0   │   b1   │   b2   │   b3   │   b4   │   b5   │   b5   │
│ int64 │ int64  │ int64  │ int64  │ int64  │ int64  │ int64  │ int64  │
├───────┼────────┼────────┼────────┼────────┼────────┼────────┼────────┤
│     0 │ 714285 │ 714286 │ 714286 │ 714285 │ 714286 │ 714285 │ 714286 │
│     1 │ 714286 │ 714286 │ 714286 │ 714286 │ 714285 │ 714286 │ 714285 │
└───────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┘
Run Time (s): real 0.051 user 0.171875 sys 0.203125
memory D with t1 as(select count(*)cnt ,a,b from t group by a,b)
         select a,
         sum(case b when 0 then cnt end)b0 ,
         sum(case b when 1 then cnt end)b1 ,
         sum(case b when 2 then cnt end)b2 ,
         sum(case b when 3 then cnt end)b3 ,
         sum(case b when 4 then cnt end)b4 ,
         sum(case b when 5 then cnt end)b5 ,
         sum(case b when 6 then cnt end)b5
         from t1 group by a;
┌───────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┐
│   a   │   b0   │   b1   │   b2   │   b3   │   b4   │   b5   │   b5   │
│ int64 │ int128 │ int128 │ int128 │ int128 │ int128 │ int128 │ int128 │
├───────┼────────┼────────┼────────┼────────┼────────┼────────┼────────┤
│     0 │ 714285 │ 714286 │ 714286 │ 714285 │ 714286 │ 714285 │ 714286 │
│     1 │ 714286 │ 714286 │ 714286 │ 714286 │ 714285 │ 714286 │ 714285 │
└───────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┘
Run Time (s): real 0.021 user 0.156250 sys 0.031250
memory D select a,
         count(case c when 0 then 1 end)c0 ,
         count(case c when 1 then 1 end)c1 ,
         count(case c when 2 then 1 end)c2 ,
         count(case c when 3 then 1 end)c3 ,
         count(case c when 4 then 1 end)c4 ,
         count(case c when 5 then 1 end)c5 ,
         count(case c when 6 then 1 end)c6 ,
         count(case c when 7 then 1 end)c7 ,
         count(case c when 8 then 1 end)c8 ,
         count(case c when 9 then 1 end)c9 ,
         count(case c when 10 then 1 end)c10
         from t group by a;
┌───────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┐
│   a   │   c0   │   c1   │   c2   │   c3   │   c4   │   c5   │   c6   │   c7   │   c8   │   c9   │  c10   │
│ int64 │ int64  │ int64  │ int64  │ int64  │ int64  │ int64  │ int64  │ int64  │ int64  │ int64  │ int64  │
├───────┼────────┼────────┼────────┼────────┼────────┼────────┼────────┼────────┼────────┼────────┼────────┤
│     0 │ 454545 │ 454545 │ 454546 │ 454545 │ 454546 │ 454545 │ 454546 │ 454545 │ 454546 │ 454545 │ 454545 │
│     1 │ 454545 │ 454546 │ 454545 │ 454546 │ 454545 │ 454546 │ 454545 │ 454546 │ 454545 │ 454546 │ 454545 │
└───────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┘
Run Time (s): real 0.061 user 0.406250 sys 0.093750
memory D with t1 as(select count(*)cnt ,a,c from t group by a,c)
         select a,
         sum(case c when 0 then cnt end)c0 ,
         sum(case c when 1 then cnt end)c1 ,
         sum(case c when 2 then cnt end)c2 ,
         sum(case c when 3 then cnt end)c3 ,
         sum(case c when 4 then cnt end)c4 ,
         sum(case c when 5 then cnt end)c5 ,
         sum(case c when 6 then cnt end)c6 ,
         sum(case c when 7 then cnt end)c7 ,
         sum(case c when 8 then cnt end)c8 ,
         sum(case c when 9 then cnt end)c9 ,
         sum(case c when 10 then cnt end)c10
         from t1 group by a;
┌───────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┐
│   a   │   c0   │   c1   │   c2   │   c3   │   c4   │   c5   │   c6   │   c7   │   c8   │   c9   │  c10   │
│ int64 │ int128 │ int128 │ int128 │ int128 │ int128 │ int128 │ int128 │ int128 │ int128 │ int128 │ int128 │
├───────┼────────┼────────┼────────┼────────┼────────┼────────┼────────┼────────┼────────┼────────┼────────┤
│     0 │ 454545 │ 454545 │ 454546 │ 454545 │ 454546 │ 454545 │ 454546 │ 454545 │ 454546 │ 454545 │ 454545 │
│     1 │ 454545 │ 454546 │ 454545 │ 454546 │ 454545 │ 454546 │ 454545 │ 454546 │ 454545 │ 454546 │ 454545 │
└───────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┘
Run Time (s): real 0.024 user 0.015625 sys 0.000000
memory D pivot(select count(*)cnt ,a,b from t group by a,b) on b using sum(cnt) ;
┌───────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┐
│   a   │   0    │   1    │   2    │   3    │   4    │   5    │   6    │
│ int64 │ int128 │ int128 │ int128 │ int128 │ int128 │ int128 │ int128 │
├───────┼────────┼────────┼────────┼────────┼────────┼────────┼────────┤
│     0 │ 714285 │ 714286 │ 714286 │ 714285 │ 714286 │ 714285 │ 714286 │
│     1 │ 714286 │ 714286 │ 714286 │ 714286 │ 714285 │ 714286 │ 714285 │
└───────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┘
Run Time (s): real 0.037 user 0.000000 sys 0.000000
memory D pivot(select count(*)cnt ,a,c from t group by a,c) on c using sum(cnt) ;
┌───────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┐
│   a   │   0    │   1    │   10   │   2    │   3    │   4    │   5    │   6    │   7    │   8    │   9    │
│ int64 │ int128 │ int128 │ int128 │ int128 │ int128 │ int128 │ int128 │ int128 │ int128 │ int128 │ int128 │
├───────┼────────┼────────┼────────┼────────┼────────┼────────┼────────┼────────┼────────┼────────┼────────┤
│     0 │ 454545 │ 454545 │ 454545 │ 454546 │ 454545 │ 454546 │ 454545 │ 454546 │ 454545 │ 454546 │ 454545 │
│     1 │ 454545 │ 454546 │ 454545 │ 454545 │ 454546 │ 454545 │ 454546 │ 454545 │ 454546 │ 454545 │ 454546 │
└───────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┘
Run Time (s): real 0.031 user 0.171875 sys 0.015625
memory D pivot t on b using count(*) group by a;
┌───────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┐
│   a   │   0    │   1    │   2    │   3    │   4    │   5    │   6    │
│ int64 │ int64  │ int64  │ int64  │ int64  │ int64  │ int64  │ int64  │
├───────┼────────┼────────┼────────┼────────┼────────┼────────┼────────┤
│     0 │ 714285 │ 714286 │ 714286 │ 714285 │ 714286 │ 714285 │ 714286 │
│     1 │ 714286 │ 714286 │ 714286 │ 714286 │ 714285 │ 714286 │ 714285 │
└───────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┘
Run Time (s): real 0.109 user 1.015625 sys 0.125000
memory D pivot t on c using count(*) group by a;
┌───────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┐
│   a   │   0    │   1    │   10   │   2    │   3    │   4    │   5    │   6    │   7    │   8    │   9    │
│ int64 │ int64  │ int64  │ int64  │ int64  │ int64  │ int64  │ int64  │ int64  │ int64  │ int64  │ int64  │
├───────┼────────┼────────┼────────┼────────┼────────┼────────┼────────┼────────┼────────┼────────┼────────┤
│     0 │ 454545 │ 454545 │ 454545 │ 454546 │ 454545 │ 454546 │ 454545 │ 454546 │ 454545 │ 454546 │ 454545 │
│     1 │ 454545 │ 454546 │ 454545 │ 454545 │ 454546 │ 454545 │ 454546 │ 454545 │ 454546 │ 454545 │ 454546 │
└───────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┘
Run Time (s): real 0.115 user 1.421875 sys 0.015625

DuckDB无论case when 7次和11次,都是先聚合更快。pivot比等价的手工case when慢一些。

sql 复制代码
SQLite version 3.52.0 2026-03-06 16:01:44
Enter ".help" for usage hints.
Connected to a transient in-memory database.
Use ".open FILENAME" to reopen on a persistent database.
sqlite> .timer on
sqlite> create table t as select i%2 a, i%7 b,i%11 c from (select value i from generate_series(1,10000000));
Run Time: real 0.803898 user 0.781250 sys 0.015625
sqlite> select a,
   ...> count(case b when 0 then 1 end)b0 ,
   ...> count(case b when 1 then 1 end)b1 ,
   ...> count(case b when 2 then 1 end)b2 ,
   ...> count(case b when 3 then 1 end)b3 ,
   ...> count(case b when 4 then 1 end)b4 ,
   ...> count(case b when 5 then 1 end)b5 ,
   ...> count(case b when 6 then 1 end)b5
   ...> from t group by a;
╭───┬────────┬────────┬────────┬────────┬────────┬────────┬────────╮
│ a │   b0   │   b1   │   b2   │   b3   │   b4   │   b5   │   b5   │
╞═══╪════════╪════════╪════════╪════════╪════════╪════════╪════════╡
│ 0 │ 714285 │ 714286 │ 714286 │ 714286 │ 714286 │ 714285 │ 714286 │
│ 1 │ 714286 │ 714286 │ 714286 │ 714286 │ 714285 │ 714286 │ 714285 │
╰───┴────────┴────────┴────────┴────────┴────────┴────────┴────────╯
Run Time: real 2.634213 user 2.515625 sys 0.109375
sqlite> with t1 as(select count(*)cnt ,a,b from t group by a,b)
   ...> select a,
   ...> sum(case b when 0 then cnt end)b0 ,
   ...> sum(case b when 1 then cnt end)b1 ,
   ...> sum(case b when 2 then cnt end)b2 ,
   ...> sum(case b when 3 then cnt end)b3 ,
   ...> sum(case b when 4 then cnt end)b4 ,
   ...> sum(case b when 5 then cnt end)b5 ,
   ...> sum(case b when 6 then cnt end)b5
   ...> from t1 group by a;
╭───┬────────┬────────┬────────┬────────┬────────┬────────┬────────╮
│ a │   b0   │   b1   │   b2   │   b3   │   b4   │   b5   │   b5   │
╞═══╪════════╪════════╪════════╪════════╪════════╪════════╪════════╡
│ 0 │ 714285 │ 714286 │ 714286 │ 714286 │ 714286 │ 714285 │ 714286 │
│ 1 │ 714286 │ 714286 │ 714286 │ 714286 │ 714285 │ 714286 │ 714285 │
╰───┴────────┴────────┴────────┴────────┴────────┴────────┴────────╯
Run Time: real 3.167292 user 3.031250 sys 0.125000
sqlite> select a,
   ...> count(case c when 0 then 1 end)c0 ,
   ...> count(case c when 1 then 1 end)c1 ,
   ...> count(case c when 2 then 1 end)c2 ,
   ...> count(case c when 3 then 1 end)c3 ,
   ...> count(case c when 4 then 1 end)c4 ,
   ...> count(case c when 5 then 1 end)c5 ,
   ...> count(case c when 6 then 1 end)c6 ,
   ...> count(case c when 7 then 1 end)c7 ,
   ...> count(case c when 8 then 1 end)c8 ,
   ...> count(case c when 9 then 1 end)c9 ,
   ...> count(case c when 10 then 1 end)c10
   ...> from t group by a;
╭───┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────╮
│ a │   c0   │   c1   │   c2   │   c3   │   c4   │   c5   │   c6   │   c7   │   c8   │   c9   │  c10   │
╞═══╪════════╪════════╪════════╪════════╪════════╪════════╪════════╪════════╪════════╪════════╪════════╡
│ 0 │ 454545 │ 454545 │ 454546 │ 454545 │ 454546 │ 454545 │ 454546 │ 454545 │ 454546 │ 454545 │ 454546 │
│ 1 │ 454545 │ 454546 │ 454545 │ 454546 │ 454545 │ 454546 │ 454545 │ 454546 │ 454545 │ 454546 │ 454545 │
╰───┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────╯
Run Time: real 3.113160 user 2.890625 sys 0.218750
sqlite> with t1 as(select count(*)cnt ,a,c from t group by a,c)
   ...> select a,
   ...> sum(case c when 0 then cnt end)c0 ,
   ...> sum(case c when 1 then cnt end)c1 ,
   ...> sum(case c when 2 then cnt end)c2 ,
   ...> sum(case c when 3 then cnt end)c3 ,
   ...> sum(case c when 4 then cnt end)c4 ,
   ...> sum(case c when 5 then cnt end)c5 ,
   ...> sum(case c when 6 then cnt end)c6 ,
   ...> sum(case c when 7 then cnt end)c7 ,
   ...> sum(case c when 8 then cnt end)c8 ,
   ...> sum(case c when 9 then cnt end)c9 ,
   ...> sum(case c when 10 then cnt end)c10
   ...> from t1 group by a;
╭───┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────╮
│ a │   c0   │   c1   │   c2   │   c3   │   c4   │   c5   │   c6   │   c7   │   c8   │   c9   │  c10   │
╞═══╪════════╪════════╪════════╪════════╪════════╪════════╪════════╪════════╪════════╪════════╪════════╡
│ 0 │ 454545 │ 454545 │ 454546 │ 454545 │ 454546 │ 454545 │ 454546 │ 454545 │ 454546 │ 454545 │ 454546 │
│ 1 │ 454545 │ 454546 │ 454545 │ 454546 │ 454545 │ 454546 │ 454545 │ 454546 │ 454545 │ 454546 │ 454545 │
╰───┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────╯
Run Time: real 3.251369 user 3.046875 sys 0.171875
sqlite>

SQLite无论case when 7次和11次,都是后聚合更快。11次的两种方法差距更小,预计更多项需要case when时会反转。

相关推荐
Deitymoon2 分钟前
嵌入式数据库——SQLite基础
数据库·sqlite
YMatrix 官方技术社区3 分钟前
美国·硅谷|YMatrix 即将亮相 Postgres Conference 2026,前瞻 AI 时代的数据基座
数据库·数据仓库·postgresql·时序数据库·ymatrix
bKYP953cL5 分钟前
构建自己的AI编程助手:基于RAG的上下文感知实现方案
数据库·人工智能·ai编程
Bert.Cai6 分钟前
MySQL DML简介
数据库·mysql
maqr_11014 分钟前
HTML怎么生成订单预览_HTML只读订单信息结构【操作】
jvm·数据库·python
2301_8038756139 分钟前
如何通过phpMyAdmin给WordPress所有用户发送全站通知_系统表插入
jvm·数据库·python
2301_777599371 小时前
mysql如何进行数据库容量规划_评估磁盘空间增长趋势
jvm·数据库·python
NineData2 小时前
NineData 亮相香港国际创科展 InnoEX 2026,以 AI 加速布局全球市场
运维·数据库·人工智能·ninedata·新闻资讯·玖章算术
m0_377618232 小时前
Redis怎样应对大规模集群的重启风暴_分批次重启节点并等待集群状态恢复绿灯后再继续操作
jvm·数据库·python
imuliuliang2 小时前
存储过程(SQL)
android·数据库·sql