PowerBI DAX 重构系列:用1个度量值代替100个 实现 动态多维度动态算法动态总计(上篇)
- 2019 年 10 月 6 日
- 筆記

概述
《PowerBI 重构》系列(代指:Power BI DAX 重构系列)将是一系列新的话题,旨在将PowerBI 技艺提升到更高的阶段。该阶段需要坚实的DAX基础,这些基础内容已经在其他文章讨论过并提供了达成方法。
如果你用过PowerBI DAX就知道写100个度量值是什么感受,今天来看一个非常落地的案例并展示如何对这样的问题进行重构。
重构,简单讲就是看原来的不顺眼,然后重新做一遍比上一次更好的。当积累的大量经验以后,就会考虑在第一次设计的时候为未来留下可以扩展的机会。这严格遵循抽象设计的 DRY原则(Don’t Repeat Youself) 以及 OCP原则(Open Close Principle),这些内容已在《用户自动运营分析》中讲过,不再重复。
背景问题
先看一个背景问题,要求从三大方面按某时间区间(如:今年)分析销售额大小,销售额排名以及销售额占比:
- 从 产品类别 方面
- 从 城市 方面
- 从 产品子类别 方面
另外,必须考虑:
- 考虑到总计行的处理
- 总计行可以按全局All或用户所选all
总计行的重要性

可以看出,Power BI自带的总计效果是远远不够的。在业务分析通常需要将局部发展态势与全局发展态势做对比,总计就是全局发展态势。
到底什么算“全部”
在理性的领域,一切内容都是精确的,因此可以被预测和控制,这里当然不例外。全部(ALL),这个词将在各位的PowerBI旅途中成为一头拦路虎(不是 路虎,是 拦路虎),要清楚的区分某些场景,全部的语义到底是什么。(这通常与企业的实际业务密不可分,而且敏感性极高,需要业务专家协同)

例如,我们刻意从上述场景来进行说明: 1、在 按产品类别 分析 销售额增长率 的 全部 指的是 绝对大全局(对,就是不受影响的总全局),因此我们需要用DAX ALL函数。 2、在 按产品子类别 分析 销售额增长率 的 全部 指的是 用户所选择的全部子类别(以用户的每次选择作为全部),因此我们需要用DAX ALLSELECTED函数。
ALLSELECTED 函数作为DAX函数中最复杂的一个,对,你没看错,是最复杂的,没有之一,复杂度超过CALCULATE,但是用起来感觉不到,此处只是指出,但不展开,当然在这里的案例也遇不到这种复杂。
好的,按类别的分析所用的度量值如下:

其中的ALL体现了绝对全局之意。
这已经有了,现在来写按类别的分析所用的度量值如下:

其中的ALLSELECTED体现了用户所选之意。
问题来了,当你问业务专家说,这里的全部到底是什么,最可怕的回答来了:都有可能的。然后,业务专家还要补一句:可不可以让用户来选择。对于打造豪华PowerBI报告的设计师当然不能回答不可以,必须回答:可以的。(PowerBI的限制只在于PowerBI的绝对物理限制,甚至要靠想象力和创造力来超过微软现在尚未提供的)PowerBI设计师会继续和业务专家确认诸如除非用户显式指定,否则默认按全局总计(即ALL)的方式来处理。
于是,5分钟后,给业务专家看到这样的效果:

(DAX 计算公式稍后给出)
由于用户选择了按全局总计,可以看到结果是正确的。这样的按钮式切片器非常强大,它可以让用户在实际使用时做出动态的选择。
至此,通过重构,我们已经有了可以动态选择总计方式的总计行。
重复的梦魇
在上述总计行的问题中,解决之后,新的问题来了,我们要对:
- 从 产品类别 方面
- 从 城市 方面
- 从 产品子类别 方面
- 从 … 方面
针对 [销售额同比增长率] 至少要写多少个度量值?
DAX公式数 = 可能的维度数 × 可能的度量值数 × 总计方式(2个)
以 5 个维度以及 10 个度量值来看,一共就要写 100 个DAX公式了。
可以慢慢写DAX公式了,由于所有的逻辑基本一致,只是在判断总计的位置有区别:
SELECTEDVALUE( ‘产品’[类别] ) = “总计” SELECTEDVALUE( ‘产品’[子类别] ) = “总计”
大家可以通过下载示例文件自行思考。这里的实现将在下篇详细展开。
总结
模式,是可以重复使用的套路。在这里我们给出三个模式:
- 总计行模式(已讨论)
- 算法选择模式(已讨论)
- 维度扩展模式(待续)
以上为非正式名称,未来可能会重新命名以形成一套系列。
在算法选择模式的按何种算法计算总计的DAX公式如下:

号称用1个度量值处理100个度量值的方式我们留在下篇。
–