kimball维度建模的维度表技术

在维度建模过程中,维度表的设计和生成是非常重要的一环。维度表中的内容反映的是事实发生的环境,对数据仓库系统可解释性和可用性起到了很重要的作用。可以说,维度表设计的好坏很大程度上决定了数据仓库的成败。在维度表的设计和字段的解释说明上,是值得投入大量的精力的。

在实际的设计过程中,需要考虑的问题有很多,这篇文章提的三点在工作中比较常见和重要的。

1. 一致性维度

Kimball在他的书中提到了一个概念是“企业数据仓库总线架构”,是一种构建企业数据仓库的方法,其核心基础就是一致性维度。一致性维度的简单说就是共享维度,对公司内所有的业务或者说事实表,统一的进行维度设计。在实践过程中,不仅包括,不同的事实表使用相同的维度表,还有不同的维度表使用相同名称相同含义的维度字段。例如,商品维度表中跟品牌相关的字段要跟品牌维度表完全一致。

一致性维度一个显著的好处,就是可以跨事实表分析,可以简单的把不同事实表中的信息合并到同一张报表中。

2. 维度的粒度

维度信息一般是包含层级关系,每条维度记录对应最细粒度的一条数据。例如商品表中有“分类-品牌-商品”三层信息,每个商品对应一条数据。一般情况下,层级数据是整齐,每个商品都有自己的品牌和分类,这种情况下比较好处理。但是有些时候需要考虑维度深度不同,或者需要可以增加深度缺失记录的情况。

例如,地理位置维度表的深度是参差不齐的,不同级别的城市需要的层级差别很大,在实际使用中,我们并不是把不存在的级别留空,而是对位置维度表重新设计来满足具体的使用情况。

城市id 城市名 区名 所属地级市 所属省份
1 上海 黄浦区 上海 上海
2 苏州 姑苏区 苏州 江苏
3 昆山 昆山 苏州 江苏

还有情况是需要额外添加深度缺失的记录,来适应事实中可能的字段缺失。例如,我们有一个页面位置维度表,用来描述页面上每个具体的问题,包括大区域、小区域和位置索引三个层级,但是位置索引并不是在所以的操作源数据中都存在,需要增加深度缺失的记录。

位置id 大区域 小区域 位置索引
1 推荐 精彩推荐 1
2 推荐 精彩推荐 2
3 推荐 精彩推荐 未知

3. 缓慢变化维

最后说一下缓慢变化维,这个也是维度设计中必须要考虑的问题。业务数据中某些字段会随着时间变化是正常的,数据仓库需要用缓慢变化维的方式来处理这种变化,常见的处理方式有如下几种:

3.1 直接覆盖

根据业务的需求,某些字段的值可能只需要直接修改就好。例如商品名称,如果只是为了在报表中展示用,而名称的修改只可能是文字的优化,那就直接改为新名字就好。但是要注意名称直接变化对统计可能带来的影响,评估基于旧名称生成的数据是否需要重新生成。

3.2 多列属性

多列属性就是通过多列的方式去存储不同时期的值,适用面比较窄,主要是一些变更次数严格限制,或者只关心最近变更的情形。

用户id 用户名(userName) 曾用名 (oldUserName)
u001 张三 张小三
u002 李明 null

3.3 增加新行

这种处理方式是每次数据发生变更就增加一行,是一种最常见的处理缓慢变化维的方式。这样会导致同样的一个自然业务主键(例如用户id)会存在多条,那么我们就需要一个更加一般化的键来确定唯一的行,常见有有两种方式来实现。

3.3.1 拉链表

因为每个自然键在维度表中可能有多条,需要额外的字段来标识,一种很容易想到的方式就是增加时间字段,例如

用户id 用户名 app版本号 生效时间 失效时间
u001 张三 3.1.2 2018-08-16 09:02:44 2018-09-10 11:23:01
u001 张三 3.1.3 2018-09-10 11:23:01

通过生效时间和失效时间字段可以成功的把维度的变化记录下来。但是拉链表在使用的时候存在一个小问题,就是每次在使用的时候都必须在sql中包含生效时间和失效时间的过滤。这个对数据分析人员是一个不算小的负担,并且可能因为忘记导致统计结果的问题。

3.3.2 代理键

代理键的方法就是生成一个新的键作为维度表的唯一键,一般是依次递增的数字。代理键做为跟事实表上跟维度表关联的外键,而不再是自然主键。

代理键 用户id 用户名 app版本号 生效时间 失效时间
1 u001 张三 3.1.2 2018-08-16 09:02:44 2018-09-10 11:23:01
2 u001 张三 3.1.3 2018-09-10 11:23:01

上面的方式,除了代理键外,依然保留了拉链表中的生效和失效时间,也可以考虑用一个布尔值的“是否是当前生效字段”替代。

代理键的方案可以让分析人员在使用过程中只需要用key关联就好,不需要关心时间字段。但是代理键也并不是十全十美的,可能带来的是自身维护的问题,在ETL中维护自增id带来的成本可能会比想象中的大。

3.4 增加快速变化附属维度

如果维度表的列比较多,大部分的字段几乎不变,少量字段变化相对较多,那么可以考虑附属维度的方式。将变化快速的字段单独组成附属维度,与原有维度相关联,形成的数据结构类似于雪花模式。鉴于之前的文件说明过,并不推荐使用雪花模式,附属维度也应当谨慎使用。