研究《DAX查询计划 白皮书》中的案例(五)优化方案3

这是本系列的最后一个优化方案,这一篇的优化方案3是所有方案中最优秀的,它解决了优化方案2中产生的[RowNumber] 问题,使整个底层计算过程中全部步骤都没有出现数据量超过万行的情况,使性能获得了极大的提升!


研究《DAX查询计划 白皮书》中的案例(一)初始方案
研究《DAX查询计划 白皮书》中的案例(二)优化方案1
研究《DAX查询计划 白皮书》中的案例(三)优化方案(番外)
研究《DAX查询计划 白皮书》中的案例(四)优化方案2
研究《DAX查询计划 白皮书》中的案例(四)优化方案3


优化方案3

DAX 查询

// 优化方案3(修正)
EVALUATE
ADDCOLUMNS (
    VALUES ( 'Calendar'[Date] ),
    "Open Orders",
        SUMX (
            FILTER (
                GENERATE (
                    SUMMARIZE (
                        Sales,
                        Sales[OrderDate],
                        Sales[ShipDate],
                        "Rows", COUNTROWS ( Sales )
                    ),
                    DATESBETWEEN ( 
                        'Calendar'[Date], 
                        Sales[OrderDate] + 1,  // 修正此处,原版是 Sales[OpenDate]
                        Sales[ShipDate] - 1 )
                ),
                'Calendar'[Date] = EARLIER ( 'Calendar'[Date] )
            ),
            [Rows]
        )
)

运行效率

以连续5次冷启动的结果进行统计,将各方案的情况列写在表格里,数字下方括号里记录的是相对前一个方案的性能变化情况。

优化方案3的表现非常亮眼,计算效率超过了之前全部的方案,总耗时已经接近个位数!

环境 参数 初始方案 优化方案1 优化方案2 优化方案(番外) 优化方案3
环境1 平均总耗时(毫秒) 4389.4 290.4
(↑ 93.38%)
79.6
(↑ 72.59%)
56.8
(↑ 28.64%)
SE耗时
(毫秒)
14.4 4.8
13.6
4.8
SE占比 0.328% 1.653%
(↑ 403.83%)
17.09%
(↑ 933.67%)
8.45%
(↓50.54%)
环境2 平均总耗时(毫秒) 4017.0 300.60
(↑ 92.52%)
76.4
(↑ 74.58%)
53.8
(↑ 29.58%)
12.8
(↑ 83.25%)
SE耗时
(毫秒)
17.2 5.8
(↑ 66.28%)
18.2
5
3.4
SE占比 0.428% 1.929%
(↑ 350.62%)
23.82%
(↑ 1134.64%)
9.29%
(↓ 60.99%)
26.56%
(↑ 11.50%)

白皮书中没有对此方案进行任何分析,留给读者实践,下面是我对该方案进行分析的详细记录。

存储引擎部分

依然首先查看存储引擎执行了哪些 xmSQL 查询

image

左侧窗口记录 SE Cache 为 1,表明有一个 xmSQL 被复用。右侧窗口记录了 4 行 Scan,其中 Line2 和 Line 4 是完全相同的,Line4 复用了 Line2 。

存储引擎一共执行 3 个 xmSQL:

1、VQ1

Line2 和 Line4,从 Calendar 表中获取 [Date] 的不重复值,包含 1 列,共 1081 行

‘Calendar’[Date]

// xmSQL VQ1
SELECT
    'Calendar'[Date]
FROM 'Calendar';

2、VQ2

Line6,对 Sales 表以 Sales[OrderDate]、Sales[ShipDate] 分组并计算行数,包含 2 个数据列和 1 个值列,共 1081 行

Sales[OrderDate], Sales[ShipDate], COUNT

// xmSQL VQ2
SELECT
    'Sales'[OrderDate],
    'Sales'[ShipDate],
    COUNT ( )
FROM 'Sales';

部分结果类似

image

3、VQ3

Line8,对 Sales 表以 Sales[OrderDate]、Sales[ShipDate] 分组,即获取 Sales 表中{Sales[OrderDate], Sales[ShipDate]} 的不重复值对,共 1081 行

Sales[OrderDate], Sales[ShipDate]

// xmSQL VQ3
SELECT
    'Sales'[OrderDate],
    'Sales'[ShipDate]
FROM 'Sales';

部分结果为:

image

存储引擎部分 3 个 xmSQL 查询都没有出现 [RowNumber]。

公式引擎部分

逻辑查询计划

AddColumns: RelLogOp DependOnCols()() 0-1 RequiredCols(0, 1)('Calendar'[Date], ''[Open Orders])
├── Scan_Vertipaq: RelLogOp DependOnCols()() 0-0 RequiredCols(0)('Calendar'[Date])
└── SumX: ScaLogOp DependOnCols(0)('Calendar'[Date]) Integer DominantValue=BLANK
    ├── Filter: RelLogOp DependOnCols(0)('Calendar'[Date]) 1-4 RequiredCols(0, 1, 2, 3, 4)('Calendar'[Date], 'Sales'[OrderDate], 'Sales'[ShipDate], ''[Rows], 'Calendar'[Date])
    │   ├── CrossApply: RelLogOp DependOnCols()() 1-4 RequiredCols(1, 2, 3, 4)('Sales'[OrderDate], 'Sales'[ShipDate], ''[Rows], 'Calendar'[Date])
    │   │   ├── AddColumns: RelLogOp DependOnCols()() 1-3 RequiredCols(1, 2, 3)('Sales'[OrderDate], 'Sales'[ShipDate], ''[Rows])
    │   │   │   ├── GroupBy_Vertipaq: RelLogOp DependOnCols()() 1-15 RequiredCols(1, 2)('Sales'[OrderDate], 'Sales'
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值