首页/数据/NoSQL 速查/分析建模:星型模型与预聚合落地
选型与架构50 条

分析建模:星型模型与预聚合落地

分析库建模先决定事实表粒度与常用过滤维度,再决定预聚合程度:ClickHouse 等列式库不支持高频 join,常把维度冗余进宽表(大宽表),并用物化视图维护聚合结果;牺牲存储与写入复杂度换查询延迟。

NoSQL 速查数据更新于 2026-10-13

分析建模的取舍

分析库建模要先定两件事:事实表的粒度(一行代表什么业务事件)和常用过滤维度,然后决定预聚合到什么程度。ClickHouse 这类列式库不擅长高频 join,实践中常把维度冗余进事实表形成宽表,再用物化视图在写入时增量维护聚合结果;本质是用存储与写入复杂度换查询延迟。维度会变的业务要额外考虑回填路径。

基本信息

表角色事实表(明细)、维表(属性)、宽表(冗余维度的明细)、汇总表(预聚合结果)
排序键MergeTree 的 ORDER BY 决定稀疏索引与数据物理顺序,应把高频过滤维度放前面
预聚合手段物化视图 + SummingMergeTree / AggregatingMergeTree,写入时增量更新
更新代价列式库擅长大批量写入,单行更新昂贵;维表变更常靠整段回填
适用引擎ClickHouse MergeTree 家族、Doris、StarRocks 等列式分析引擎

典型使用场景

  • 固定口径的看板与报表:把分钟级、小时级聚合固化,查询只读汇总表
  • 明细下钻:保留明细表并设计排序键,让下钻查询能命中索引而非全表扫描
  • 多租户分析:租户字段放在排序键首位,天然形成数据聚集并便于按租户搬迁
  • 维度属性变更:用回填任务重算受影响时间段的宽表,而不是原地更新
  • 指标口径治理:把去重方式、时区、迟到数据处理写进汇总表定义并随表版本记录

物化视图预聚合(ClickHouse 示例)

物化视图预聚合(ClickHouse 示例)
-- 明细表:按 (tenant, ts) 排序,既支撑明细查询也服务聚合回填
CREATE TABLE logs.events (
  tenant String, ts DateTime, service LowCardinality(String),
  ok UInt8, latency_ms UInt32
) ENGINE = MergeTree ORDER BY (tenant, ts);

-- 物化视图:写入时就地增量维护分钟级聚合,查询直接读汇总表
CREATE MATERIALIZED VIEW logs.events_1m
ENGINE = SummingMergeTree ORDER BY (tenant, service, minute)
AS SELECT tenant, service, toStartOfMinute(ts) AS minute,
          count() AS cnt, sum(ok) AS ok_cnt, avg(latency_ms) AS latency_avg
   FROM logs.events GROUP BY tenant, service, minute;

-- 历史数据不会自动进视图,需要手动回填一次
INSERT INTO logs.events_1m
SELECT tenant, service, toStartOfMinute(ts), count(), sum(ok), avg(latency_ms)
FROM logs.events GROUP BY tenant, service, toStartOfMinute(ts);

建模方式对照

方式优点代价
宽表查询不做 join,链路短、延迟低维度更新要回填;存储冗余放大
星型模型维表独立,更新简单查询 join 成本高,列式库上性能不稳
预聚合表查询快,扫描量小口径必须与明细一致;回填与版本管理不可省
明细表 + 排序键支持任意维度下钻没有现成聚合时可查范围大,依赖排序键设计
预聚合的口径要写清楚:去重方式、时区、是否含迟到数据、保留几位小数。口径含糊的汇总表在业务与明细对账时会互相打架,且很难判断是哪一侧算错。
物化视图只对创建之后的写入生效,历史数据必须单独回填一次,否则汇总表会安静地缺一段,查询结果看起来正常但偏低。

易错点

  • 物化视图漏掉历史回填:看板数字比明细少一截,且没有任何报错提示
  • 汇总表与明细表口径不一致又不记版本:对账出差异时无法判断哪一侧算错,只能全量重算
  • 把高频过滤字段排在排序键末尾:稀疏索引无法裁剪,明细查询退化为扫描全部数据
  • 把单行更新当常规手段:列式库按 part 合并组织数据,频繁小更新会制造大量碎片与后台合并压力

数据来源与参考

  • ClickHouse Docs: Materialized view
  • ClickHouse Docs: MergeTree
  • ClickHouse Docs: SummingMergeTree
​‌‌​​‌​​​‌‌​‌‌‌‌​‌‌​​​‌‌​‌‌‌​​‌‌​​‌​‌‌‌​​‌‌‌​​​‌​‌‌​‌​​‌​‌‌‌​​​‌​‌‌​‌​​‌​‌‌​​​‌‌​‌‌‌​‌​​​‌‌​‌‌‌‌​​‌​‌‌‌​​‌‌​​​‌‌​‌‌​‌‌‌‌​‌‌​‌‌​‌