Where和Subselect/Subcube在MDX都是经常使用的语句,有的时候它们能起到相同的效果,而有的时候却又不能,这究竟是什么原因呢?本文将尝试就这些情况作一些分析(不对之处,欢迎大家及时指出)。
以下
MDX
语句可以在
SSAS
(打了SP2补丁的版本)的示例库:
Adventure Works
中运行。
相同和不同
Where和Subselect/Subcube都能够限定计算的范围。请看下面的两个语句:
例一
SELECT
[
Measures
]
.
[
Internet Sales Amount
]
ON
0
,
[
Date
]
.
[
Calendar
]
.
[
Calendar Year
]
.Members
ON
1
FROM
[
Adventure Works
]
WHERE
[
Product
]
.
[
Product Categories
]
.
[
Category
]
.
[
Bikes
]
SELECT
[
Measures
]
.
[
Internet Sales Amount
]
ON
0
,
[
Date
]
.
[
Calendar
]
.
[
Calendar Year
]
.Members
ON
1
FROM
(
SELECT
[
Product
]
.
[
Product Categories
]
.
[
Category
]
.
[
Bikes
]
ON
0
FROM
[
Adventure Works
]
)
以上两条语句能够返回相同的计算结果(见下图),这个结果中仅仅包括Bikes的销售金额。
但是,Where和Subselect/Subcube也有不同。请看下面的两个语句:
例二
WITH
MEMBER
[
Measures
]
.
[
Category Name
]
AS
[
Product
]
.
[
Product Categories
]
.CurrentMember.MemberValue
SELECT
[
Measures
]
.
[
Category Name
]
ON
0
,
[
Date
]
.
[
Calendar
]
.
[
Calendar Year
]
.Members
ON
1
FROM
[
Adventure Works
]
WHERE
{
[
Product
]
.
[
Product Categories
]
.
[
Category
]
.
[
Bikes
]
}
WITH
MEMBER
[
Measures
]
.
[
Category Name
]
AS
[
Product
]
.
[
Product Categories
]
.CurrentMember.MemberValue
SELECT
[
Measures
]
.
[
Category Name
]
ON
0
,
[
Date
]
.
[
Calendar
]
.
[
Calendar Year
]
.Members
ON
1
FROM
(
SELECT
{
[
Product
]
.
[
Product Categories
]
.
[
Category
]
.
[
Bikes
]
}
ON
0
FROM
[
Adventure Works
]
)
它们的结果分别如下所见:
从上面的结果我们可以看出,Where语句的改变了
[
Product
]
.
[
Product Categories
]的当前Member,而Subselect/Subcube语句没有。
另外再看一种不同的情况:
例三
WITH
MEMBER
[
Measures
]
.
[
Test1
]
AS
AGGREGATE(EXISTING
[
Product
]
.
[
Product Categories
]
.
[
Subcategory
]
.Members,
[
Measures
]
.
[
Internet Sales Amount
]
)
MEMBER
[
Measures
]
.
[
Test2
]
AS
AGGREGATE(
[
Product
]
.
[
Product Categories
]
.
[
Subcategory
]
.Members,
[
Measures
]
.
[
Internet Sales Amount
]
)
SELECT
{
[
Measures
]
.
[
Test1
]
,
[
Measures
]
.
[
Test2
]
}
ON
0
,
[
Date
]
.
[
Calendar Year
]
.MEMBERS
ON
1
FROM
[
Adventure Works
]
WHERE
{
[
Product
]
.
[
Product Categories
]
.
[
Subcategory
]
.
[
Socks
]
,
[
Product
]
.
[
Product Categories
]
.
[
Subcategory
]
.
[
Road Bikes
]
}
WITH
MEMBER
[
Measures
]
.
[
Test1
]
AS
AGGREGATE(EXISTING
[
Product
]
.
[
Product Categories
]
.
[
Subcategory
]
.Members,
[
Measures
]
.
[
Internet Sales Amount
]
)
MEMBER
[
Measures
]
.
[
Test2
]
AS
AGGREGATE(
[
Product
]
.
[
Product Categories
]
.
[
Subcategory
]
.Members,
[
Measures
]
.
[
Internet Sales Amount
]
)
SELECT
{
[
Measures
]
.
[
Test1
]
,
[
Measures
]
.
[
Test2
]
}
ON
0
,
[
Date
]
.
[
Calendar Year
]
.MEMBERS
ON
1
FROM
(
SELECT
{
[
Product
]
.
[
Product Categories
]
.
[
Subcategory
]
.
[
Socks
]
,
[
Product
]
.
[
Product Categories
]
.
[
Subcategory
]
.
[
Road Bikes
]
}
on
0
FROM
[
Adventure Works
]
)
它们的结果分别如下:
上面的结果中,
[
Measures
]
.
[
Test1
]
代表当前Context的销售数量,而
[
Measures
]
.
[
Test2
]代表了总的销售数量,
我们知道Existing函数强制指定的Set在当前的Context下进行计算( http://msdn2.microsoft.com/en-us/library/ms145541.aspx),Where情况下,使用Existing的
[
Measures
]
.
[
Test1
]一切正常,而Subselect/Subcube情况下,使用Existing的
[
Measures
]
.
[
Test1
]似乎没有发生任何作用,这是什么原因呢?
分析
以上的结果,无论是相同还是不同,都和Context有关系。
我们知道:每一个Set,Member,Turple都执行在一个特定的Context中。Subselect/Subcube设定了整个Cube的Context,而Where和所有Axis一起构成了Calculate Member当前Context
。这些设定都影响了计算时的数据范围,这就是第一个例子中为何Subselect/Subcube和Where返回相同结果的原因。
接下来的例子中,Where情况下,能够返回希望的当前Member的原因在于:Where也是一个Axis,即常说的Silcer Axis,它和所有Axis设定了各个Attribute Hierarchy的当前的Member,而Subselect/Subcube对Attribute Hierarchy当前的Member没有做任何的改变。
对于第三个例子,在Subselect/Subcube情况使用Existing函数无效,说明Subselect/Subcube对当前的Context并无影响,这同时说明Subselect/Subcube和Where构成的Context并不完全相同,在不同情况下,可能采用不同的上下文。Existing失效并不妨碍Subselect/Subcube在计算时对数据范围的影响,这说明在作Cell计算(包括Calculate Member)的时候,Subselect/Subcube和Where的Context都会同时被采用(除了Context被替换的情况,就像第三个例子中的
[
Measures
]
.
[
Test2
]中
[
Product
]
.
[
Product Categories
]
.
[
Subcategory
]
.Members替换了当前Context和Cube Context中
[
Product
]
维度的当前设置一样)。
总结
Where和Subselect/Subcube都能够限定计算的范围,它们的最大不同在于,Where和所有Axis一起还设置了各个Attribute Hierarchy的当前Member。