DAX:汇总用于分组聚合的5个函数

下面列出的5个表函数,都是DAX中用于做分组聚合的函数。

ADDCOLUMNS(<table>, <name>, <expression>[, <name>, <expression>]…)
SELECTCOLUMNS(<Table>, [<Name>], <Expression>, [<Name>], …)

SUMMARIZE (<table>, <groupBy_columnName>[, <groupBy_columnName>]…[, <name>, <expression>]…)
SUMMARIZECOLUMNS( <groupBy_columnName> [, < groupBy_columnName >]…, [<filterTable>]…[, <name>, <expression>]…)

GROUPBY (<table> [, <groupBy_columnName> [, <groupBy_columnName> [, …]]] [, <name>, <expression> [, <name>, <expression> [, …]]])

DAX:【翻译】SUMMARIZE的秘密
DAX:翻译《使用SUMMARIZE和ADDCOLUMNS添加扩展列》
DAX:翻译《介绍SUMMARIZECOLUMNS》
DAX:表值函数 ADDCOLUMNS 和 SELECTCOLUMNS
DAX:GROUPBY 嵌套聚合

前言:

Row Context(行上下文)可以简单解释为同一个行的不同列。引用列做运算的操作,是在同一行中的不同列之间执行计算。

例如,Sales[Amount] 和 Sales[TotalCost] 都是引用列,这两个列是在同一行。

Gross Profit := SUMX ( Sales, Sales[Amount] – Sales[TotalCost] )

Iterator(迭代器):可以简单理解为Row Context的集合。每一次迭代都是一个Row Context。上例中的Sales就是迭代器,每一行就是一个Row Context,在每一行中执行 Sales[Amount] - Sales[TotalCost]。

一,ADDCOLUMNS

向表中添加计算列,每一个计算列在Row Context中执行计算,,就是说,Table参数的每一行都是一个Row Context,计算列都是在Row Context中执行。如果需要执行上下文转换(Context Transition),用Row Context生成Filter Context,那么需要使用CALCULATE函数。

返回的值是表所有的原始列和新增加的计算列。

注意:当发生上下文转换(Context trasition)时,新增加的列不再保留data lineage,即使是简单的列引用,也不会保留。

例如,新的计算列@Quantity Correct的表达式中包含 CALCULATE函数,执行了上下文切换。

--  ADDCOLUMNS is an iterator that returns its first argument after adding the column specified.
--  New columns are computed in the row context of ADDCOLUMNS,
--  you need to invoke context transition to generate a filter context, if needed.
EVALUATE
FILTER (
    ADDCOLUMNS (
        VALUES ( 'Date'[Calendar Year] ),
        "@Year Number",         INT ( RIGHT ( 'Date'[Calendar Year], 4 ) ),
        "@Amount",              [Sales Amount],
        "@Quantity Wrong",      SUM ( Sales[Quantity] ),
        "@Quantity Correct",    CALCULATE ( SUM ( Sales[Quantity] ) )
    ),
    [@Amount] > 0
)

二,SELECTCOLUMNS

从表中选择列,并可以向输出结果中添加新的计算列,每一个新的计算列在Row Context中执行计算。如果需要执行上下文转换(Context Transition),用Row Context生成Filter Context,那么需要使用CALCULATE函数。

注意:新增加的列除了简单的列引用之外,不会保留data lineage。也就是说,对于新增加的计算列,只有简单的列引用会保留data lineage。

--  SELECTCOLUMNS has a row context that can be used to write
--  expressions that navigate through relationships.
EVALUATE
CALCULATETABLE (
    SELECTCOLUMNS (
        Sales,
        "Order Number", Sales[Order Number],
        "Order Line Number", Sales[Order Line Number],
        "Customer", RELATED ( Customer[Name] ),
        "Product", RELATED ( 'Product'[Product Name] ),
        "Quantity", Sales[Quantity],
        "Line Amount", Sales[Quantity] * Sales[Net Price]
    ),
    'Date'[Date] = DATE ( 2007, 9, 19 ),
    Customer[Customer Type] = "Person"
)

三,SUMMARIZE

该函数谨慎使用,GroupBy_ColumnName 列必须是table参数的原始列,或者跟table参数有关联,并且不推荐用于添加新的计算列,推荐使用ADDCOLUMNS来添加新的计算列。

--  SUMMARIZE can also create new columns like ADDCOLUMNS does even though we strongly discourage using this feature due
--  to the complexity of the result in some scenarios.
--  Columns are computed in both a row and a filter context filtering the currently iterated row.
EVALUATE
CALCULATETABLE (
    SUMMARIZE (
        Sales,
        'Product'[Brand],
        'Date'[Calendar Year],
        "Qty", SUM ( Sales[Quantity] ),
        "Brand & Year", 'Product'[Brand] & " - " & 'Date'[Calendar Year]
    ),
    'Product'[Color] = "Silver Grey"
)

四,SUMMARIZECOLUMNS

先来解释函数的前两个参数,这两个参数都可以重复多次:

  • GroupBy_ColumnName:用于分组的列
  • FilterTable:用于定义data rows的范围。

返回值是一个表,包含GroupBy_ColumnName和新的计算列,且计算列不能包含blank。

注意:SUMMARIZECOLUMNS 把同一张表上的所有过滤器组合成一个过滤器,此过滤器生成的组合表仅包含 SUMMARIZECOLUMNS 中明确列出的作为分组列(GroupBy_ColumnName)的列或过滤器中的列。这是自动存在(auto-exists)的行为,对 FILTERS 等函数有副作用。

SUMMARIZECOLUMNS 中的过滤器仅适用于来自于同一张表的分组列(GroupBy_ColumnName)和度量值,也就是说,如果过滤器是A表,那么过滤器会直接过滤来自于A表的Groupby_ColumnName参数。

虽然不能直接过滤来自于其他表的分组列,但是可以通过度量值中隐含的非空过滤器间接进行过滤,也就是说,过滤器会直接或间接对Measure进行过滤。为了无条件地将过滤器应用于分组列,建议 SUMMARIZECOLUMNS 的 CALCULATETABLE 函数应用过滤器。

--  Blank values are automatically removed from the output, unless you use the IGNORE modifier for newly introduced columns.
--  Removed rows can also be reintroduced later by using ADDMISSINGITEMS
EVALUATE
SUMMARIZECOLUMNS (
    'Date'[Calendar Year],
    "Amount", [Sales Amount]
)
 
EVALUATE
ADDMISSINGITEMS (
    'Date'[Calendar Year],
    SUMMARIZECOLUMNS (
        'Date'[Calendar Year],
        "Amount", [Sales Amount]
    ),
    'Date'[Calendar Year]
)
ORDER BY 'Date'[Calendar Year]

 五,GROUPBY函数

GROUPBY函数用来聚合前一个表表达式中计算列的结果,通常用于嵌套聚合。

参数解释:

  • Table:迭代器,每一行都是一个Row Context。
  • GroupBy_ColumnName:用于分组的列 

返回的结果中包含GroupBy_ColumnName参数和新增的计算列。GROUPBY函数只能用在当前的分组(CURRENT GROUP)中。 

函数CURRENTGROUP()只能用于GROUPBY()函数中,表示当前的分组。

--  GROUPBY is useful to group by columns with no lineage
--  Each column added by GROUPBY must iterate CURRENTGROUP().
--  Moreover, you cannot use CALCULATE inside a GROUPBY iteration.
DEFINE
VAR AverageCustomerSales =
    AVERAGEX ( Customer, [Sales Amount] )
VAR TaggedCustomers =
    SUMMARIZECOLUMNS (
        Customer[CustomerKey],
        "Customer Category",
            IF ( [Sales Amount] >= AverageCustomerSales, "Above Average", "Below Average" )
    )
VAR Result =
    GROUPBY (
        TaggedCustomers,
        [Customer Category],
        "# Customers", COUNTX ( CURRENTGROUP (), 1 )
    )
EVALUATE
    Result

 

 

参考文档:

 

posted @ 2025-02-12 18:16  悦光阴  阅读(140)  评论(0)    收藏  举报