union all动态表_Power BI可视化技巧:时间维度动态折叠显示

本文介绍了如何在Power BI中使用union all动态表实现日期维度的动态折叠显示,从日到周、月、季、年的汇总。作者提供了一种思路,通过DAX新建表和构建度量值,特别是核心度量的详细解析,帮助读者理解如何处理日期界的判断和折叠逻辑。此外,文章强调了动手前理清逻辑、建立测试度量以及注意代码细节的重要性。
摘要由CSDN通过智能技术生成

​作者/Beau
数据分析爱好者,擅长PBI数据分析

本文灵感来自于星球球友的一个求助帖,他的诉求是可以在矩阵中对于日期类型的列标题进行动态折叠显示。

何为折叠呢?

简单的说就是当切片器选择日期长度超过一周时,则折叠为周维度显示,以此类推,可由日折叠为周,周折叠为月,月折叠为季,季折叠为年,换句话说就是日期由低纬度向高维度的汇总。

还是不明白?那就直接看效果图。

4ed14fd034cf2702eb1012dfc512bb05.gif

特别提醒:

为了便于大家理解,核心度量值代码已在源文件中做了详细注释哦。

闲话不多说,切入正题。

制作步骤

1、模型概览

cca80bd472b7f62f7e261c84186f5ec4.png

模型是不是很简单?原生的三个表以及一个自建维度表,这里只建了三个度量值,所以就没有建专门的度量值表。

关键点:

1.这里的日期表包含列的颗粒度应尽可能的细,如下图所示,原因在于这样处理会便于后期日期维度表的创建。

ae5b7515cf2e80b8f1262769ed4b5af7.png

2.对于日期表中的日名称和周名称的建立是有技巧的,日名称要包含年月,周名称要包含年,如下图所示。这样处理的目的在于我们能够方便的锁定目标数据。

fc1915cbc51d44fad8fc5960b117fcfa.png

2、构造辅助表

使用DAX新建表,如下

日期维度表=
VAR y =    ADDCOLUMNS (        SELECTCOLUMNS(            SUMMARIZE( '日期', '日期'[年份名称], '日期'[年份序号], '日期'[日期] ),            "年份", '日期'[年份名称],            "维度明细", '日期'[年份名称],            "日期", '日期'[日期],            "orderby",0        ),        "类别名称", "年"    )
VAR q =    ADDCOLUMNS (        SELECTCOLUMNS(            SUMMARIZE( '日期', '日期'[年份名称], '日期'[季度名称], '日期'[季度序号], '日期'[日期] ),            "年份", '日期'[年份名称],            "维度明细", '日期'[季度名称],            "日期", '日期'[日期],            "orderby",1        ),        "类别名称", "季"    )
VAR m =    ADDCOLUMNS (        SELECTCOLUMNS(            SUMMARIZE( '日期', '日期'[年份名称], '日期'[月份名称], '日期'[月份序号], '日期'[日期] ),            "年份", '日期'[年份名称],            "维度明细", '日期'[月份名称],            "日期", '日期'[日期],            "orderby",2        ),        "类别名称", "月"    )
VAR w =    ADDCOLUMNS (        SELECTCOLUMNS(            SUMMARIZE( '日期', '日期'[年份名称], '日期'[周名称], '日期'[周序号], '日期'[日期] ),            "年份", '日期'[年份名称],            "维度明细", '日期'[周名称],            "日期", '日期'[日期],            "orderby",3        ),        "类别名称", "周"    )
VAR d =    ADDCOLUMNS (        SELECTCOLUMNS(            SUMMARIZE( '日期', '日期'[年份名称], '日期'[日名称], '日期'[日值], '日期'[日期] ),            "年份", '日期'[年份名称],            "维度明细", '日期'[日名称],            "日期", '日期'[日期],            "orderby",4        ),        "类别名称", "日"    )
RETURN    UNION ( y, q, m, w, d )

核心思想在于利用原生日期表日期数据进行汇总合并。

这里要注意"orderby"列字段的创建规则,从日-年按照1-4的顺序创建,这样处理是为了在可视化组件中可以按照从左往右的顺序逐级折叠。

3.建立度量值

需要建立的具体度量值如下所示。

e99e9c5413271c6d603682340b5c2fbc.png

[salse]为基础度量值,这里不再赘述。

[test]度量值为测试度量值,它并没有直接参与到最终的数据呈现中,那我为何要建立它呢?各位小伙伴可不要小看它的作用,在我们日常写特别复杂的度量时,经常会被上下文环境弄晕头,那么这个度量就是解决此问题的利器,你可以将复杂度量中的步骤一一拆解写入到测试度量中,以验证每一步的结果是否符合预期,这将使你的工作事半功倍。

前方高能!核心度量即将登场!(代码比较长,请耐心看完。)

view=--根据切片器取对应值
VAR select_d =   SELECTEDVALUE ( '日期'[日名称])VAR select_w =   SELECTEDVALUE ( '日期'[周名称])VAR select_m =   SELECTEDVALUE ( '日期'[月份名称] )
VAR select_q =   SELECTEDVALUE ( '日期'[季度名称] )
VAR select_y =   SELECTEDVALUE ( '日期'[年份名称] )--对周界点进行判断
VAR tf_w =    MOD (SELECTEDVALUE ( '日期'[周值] ), 7 )--判断当前上下文字段
VAR findd =    FIND ("D", SELECTEDVALUE ( '日期维度表'[维度明细] ),, 0 ) = 7
VAR findw =    FIND ("W", SELECTEDVALUE ( '日期维度表'[维度明细] ),, 0 ) = 5
VAR findm =    FIND ("M", SELECTEDVALUE ( '日期维度表'[维度明细] ),, 0 ) = 5
VAR findq =    FIND ("Q", SELECTEDVALUE ( '日期维度表'[维度明细] ),, 0 ) = 5
VAR findy =    FIND ("Y", SELECTEDVALUE ( '日期维度表'[维度明细] ),, 0 ) = 1--求当前维度的下级维度最小值
VAR min_w_d =    CALCULATE( MIN ( '日期'[日名称] ), FILTER (ALL ( '日期' ), [周名称] = select_w) )
VAR min_m_w =    CALCULATE( MIN ( '日期'[周名称] ), FILTER (ALL ( '日期' ), [月份名称] = select_m) )VAR min_q_m =    CALCULATE( MIN ( '日期'[月份名称] ), FILTER (ALL ( '日期' ), [季度名称] = select_q) )VAR min_y_q =    CALCULATE( MIN ( '日期'[季度名称] ), FILTER (ALL ( '日期' ), [年份名称] = select_y) )--返回结果
RETURN    
SWITCH ( TRUE(),        
findd && SELECTEDVALUE ( '日期维度表'[维度明细] ) <= select_d && SELECTEDVALUE ( '日期维度表'[维度明细] ) >= min_w_d           && tf_w = 0 , CALCULATE ( [salse], TREATAS ( VALUES ( '日期维度表'[日期] ), '日期'[日期] ) ),        
findw&& SELECTEDVALUE ( '日期维度表'[维度明细] ) <= select_w&&SELECTEDVALUE ( '日期维度表'[维度明细] )>= min_m_w           && tf_w = 0 , CALCULATE ( [salse], TREATAS ( VALUES ( '日期维度表'[日期] ), '日期'[日期] ) ),        
findw&& SELECTEDVALUE ( '日期维度表'[维度明细] ) < select_w&& SELECTEDVALUE ( '日期维度表'[维度明细] ) >= min_m_w           && tf_w > 0, CALCULATE ( [salse], TREATAS ( VALUES ( '日期维度表'[日期] ), '日期'[日期] ) ),        
findm&& SELECTEDVALUE ( '日期维度表'[维度明细] ) < select_m&& SELECTEDVALUE ( '日期维度表'[维度明细] ) >= min_q_m,           CALCULATE ( [salse], TREATAS ( VALUES ( '日期维度表'[日期] ), '日期'[日期] ) ),        
findq&& SELECTEDVALUE ( '日期维度表'[维度明细] ) < select_q && SELECTEDVALUE ( '日期维度表'[维度明细] ) >= min_y_q,           CALCULATE ( [salse], TREATAS ( VALUES ( '日期维度表'[日期] ), '日期'[日期] ) ),        
findy&& SELECTEDVALUE ( '日期维度表'[维度明细] ) < select_y,  CALCULATE ( [salse], TREATAS ( VALUES ( '日期维度表'[日期] ), '日期'[日期] ) )    )
 

不要被它的长度吓到,代码的长度和难度并不成正比哦,下面重点对此度量进行剖析:

为了便于理解,我将代码分成了四个部分:

  • 提取切片值
  • 对周界点判断
  • 对当前上下文字段进行判断
  • 求当前日期维度的下级维度最小值
  • 返回结果

讲之前啰嗦几句,类似这种关于日期的动态展示,关键点在于逻辑的梳理,不要一上来就开始写代码,最好先在纸上将每一步需要满足的条件画出来,逐步拆解,以便于对各日期界点清晰的判断,从而做到全盘考量,不会遗漏任何细节,才能最终得出想要的结果。碍于篇幅所限,就不展开讲了。

这里重点说一下度量的第二部分和第五部分,其余部分可以看源文件中的注释自行理解。

对周界点判断部分

这里采用取余函数进行判断,例如我们这里需要判断2011年3月23号是其所在周的周几,如果余数是0,则表示该天是星期日。可能细心的小伙伴会问,为何这里你只对周界点进行判断,那月度,季度,和年份界点呢?别着急,往下继续看。

返回结果部分

看着虽长,但是通过代码格式化后可看出基本范式是一样的,会写一种,写其他的都手到擒来。

发现了没?为何这里的日维度和周维度的变量和别的都不一样?看着有些复杂?

揭晓答案,根据触发点的不同,其实这里我对日期是做了两种折叠展现方式,哪两种呢?

1.触发点在当日,比如1月9日为周日,当切片器选择1月9日时,会立即折叠为周,缺点显而易见,1月9日的数据无法看到。

2.触发点在次日,同样用上述例子,当切片器选择1月9日时,并不会触发折叠,而是当切片器选择1月10日时,会触发折叠,优点也是显而易见的,这样每天的数据都能得到展现。

个人倾向于使用第二种方式,数据会得到完整展示,而且代码量也会少很多。当然小伙伴们可以视情况自由选择。

这里同样采取了无侵入的设计思路,尽量少的建立表关系,而通过TREATAS实现虚拟关联。

这一部分是整体代码的核心所在,也是难点所在,不要奢望一下能写出结果,要勇于试错,同时要注意细节,多一个或者少一个"="都会让你原地打转很久,所以一定要提前梳理清楚逻辑。

4.制作可视化

可视化没什么好说的,将建好的度量放入矩阵中,放入柱状图也是不错的选择。效果如下图所示:

3b33ea8151f36ab77626fe4a9cb1fd51.png

写在最后

最后让我们一起对本文重点内容进行回顾总结:

1.动手之前做导图,理清逻辑。

2.可建立测试度量,方便验证。

3.写代码注意细节,避免遗漏。

可能有的小伙伴会说这种需求在实际工作中遇到的很少,将不同的日期维度放在一起展示进行比较没有实际意义,但我想说的是这里面的思维和实现过程是值得学习借鉴的,掌握了它,相信大家以后对于处理大部分的日期维度问题将会更游刃有余。

本文是基于对单日期切片,如果想对一段日期实现此效果呢?是否可以加入一个日期维度切片,更便于比较?等等一系列的问题,我在这里抛砖引玉,更多的可能等待着小伙伴们去探索发现。还是那句话:能做的还有很多,这仅仅只是开始。

-精彩推荐-

采悟:使用Power BI进行动态帕累托分析​zhuanlan.zhihu.com
bc1967fce5f2503152439928e38ddc0c.png
采悟:PowerBI分析模型:产品关联度分析​zhuanlan.zhihu.com
5d331dc89913698d3c7d8737f0215385.png
采悟:如何使用Power BI计算新客户数量?​zhuanlan.zhihu.com
bd591d8a1890f72a8a7ff01020729996.png

喜欢了别忘了点赞哦。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值