[Mondrian] .Children function not being evaluated natively (no join with the fact table)

Robin Tharappel rtharappel at gmail.com
Tue May 12 15:49:11 EDT 2009


Hello,

With Mondrian 3.0.4 it appears that the .children function is not
being evaluated natively when specified inside of NON EMPTY set. It
will return empty children as well.  This can be a performance problem
if the dimension contains a large number of members at the children
level.  By joining the dimension table with the fact table the number
of members could be reduced . This is the MDX query with the
FoodMart.xml.


with set [#DataSet#] as '{[Product].[All Products].[Food].[Baking
Goods].[Baking Goods].Children}'
select {[Measures].[Store Invoice], [Measures].[Supply Time],
[Measures].[Warehouse Cost], [Measures].[Warehouse Sales]} ON COLUMNS,
 NON EMPTY Hierarchize({[#DataSet#]}) ON ROWS
from [Warehouse]
where ([Time].[1997].[Q4].[12])


The root cause of this problem is that for this expression
“[Product].[All Products].[Food].[Baking Goods].[Baking
Goods].Children”, the RolapEvaluator’s nonempty is true, but the
RolapEvaluator.root.slicerEvaluator’s nonEmpty property is still
false. They are out of sync.

The RolapEvaluator.evaluateNamedSet(String, Exp) method will call the
root.evaluateNamedSet(String, Exp). And it will pass the
root.slicerEvaluator to the
FunUtil.getNonEmptyMemberChildren(Evaluator, Member) method for the
.Children call, which will use this nonEmpty property of the
slicerEvalutor to determine weather to return the nonEmpty children or
not.


But if I made this change in
RolapResult$RolapResultEvaluatorRoot.evaluateNamedSet(String, Exp)
line: 1194  to sync the slicerEvaluator’s nonEmpty with Evaluator’s
nonEmpty value. It would break these three unit tests.

testTopMetricWithThreeLevelHierarchy (mondrian.test.TopBottomTest
testTotalingWhenIgnoreUnrelatedDimensionsPropertyIsTrue(mondrian.test.IgnoreUnrelatedDimensionsTest
testIndependentSlicerMemberNonNative(mondrian.rolap.NonEmptyTest


Note that if the .Children function is replaced by an equivalent
Descendants function it will be evaluated by joining with the fact
table. Any suggestion for this problem?

Thanks



The trace stack for the .Children call:
Thread [main] (Suspended)
            SqlMemberSource.chooseAggStar(MemberChildrenConstraint,
RolapMember) line: 581
            SqlMemberSource.makeChildMemberSql(RolapMember,
DataSource, MemberChildrenConstraint) line: 502
            SqlMemberSource.getMemberChildren2(RolapMember,
List<RolapMember>, MemberChildrenConstraint) line: 836
            SqlMemberSource.getMemberChildren(RolapMember,
List<RolapMember>, MemberChildrenConstraint) line: 770
            SqlMemberSource.getMemberChildren(List<RolapMember>,
List<RolapMember>, MemberChildrenConstraint) line: 745
            SmartMemberReader.readMemberChildren(List<RolapMember>,
List<RolapMember>, MemberChildrenConstraint) line: 237
            SmartMemberReader.getMemberChildren(List<RolapMember>,
List<RolapMember>, MemberChildrenConstraint) line: 201
            RolapCubeHierarchy$RolapCubeHierarchyMemberReader.readMemberChildren(List<RolapMember>,
List<RolapMember>, MemberChildrenConstraint) line: 472
            RolapCubeHierarchy$RolapCubeHierarchyMemberReader.getMemberChildren(List<RolapMember>,
List<RolapMember>, MemberChildrenConstraint) line: 568
            RolapCubeHierarchy$RolapCubeHierarchyMemberReader(SmartMemberReader).getMemberChildren(RolapMember,
List<RolapMember>, MemberChildrenConstraint) line: 169
            RolapCube$RolapCubeSchemaReader(RolapSchemaReader).internalGetMemberChildren(Member,
MemberChildrenConstraint) line: 155     //Here is
DefaultMemberChildrenConstraint
            RolapCube$RolapCubeSchemaReader(RolapSchemaReader).getMemberChildren(Member,
Evaluator) line: 145       //Here the Evaluator is null
            RolapCube$RolapCubeSchemaReader(RolapSchemaReader).getMemberChildren(Member)
line: 139
            Query$QuerySchemaReader(DelegatingSchemaReader).getMemberChildren(Member)
line: 60
            FunUtil.getNonEmptyMemberChildren(Evaluator, Member) line:
1790
            BuiltinFunTable$30$1.evaluateList(Evaluator) line: 906
            SetFunDef$ListSetCalc$1.evaluateVoid(Evaluator) line: 131
            SetFunDef$ListSetCalc.evaluateList(Evaluator) line: 204
            SetFunDef$ListSetCalc(AbstractListCalc).evaluate(Evaluator)
line: 67
            RolapResult.evaluateExp(Calc, RolapEvaluator) line: 794
            RolapResult.access$100(RolapResult, Calc, RolapEvaluator)
line: 46
            RolapResult$RolapResultEvaluatorRoot.evaluateNamedSet(String,
Exp) line: 1194
            RolapEvaluator.evaluateNamedSet(String, Exp) line: 884
            NamedSetExpr$1.evaluateList(Evaluator) line: 78
            SetFunDef$ListSetCalc$1.evaluateVoid(Evaluator) line: 131
            SetFunDef$ListSetCalc.evaluateList(Evaluator) line: 204
            HierarchizeFunDef$1.evaluateList(Evaluator) line: 48
            HierarchizeFunDef$1(AbstractListCalc).evaluate(Evaluator) line: 67
            RolapResult.executeAxis(Evaluator, QueryAxis, Calc,
boolean, RolapResult$AxisMember) line: 694
            RolapResult.evalLoad(List<Member[]>, int, Evaluator,
QueryAxis, Calc, AxisMember) line: 557
            RolapResult.loadMembers(List<Member[]>, RolapEvaluator,
QueryAxis, Calc, AxisMember) line: 532
            RolapResult.<init>(Query, boolean) line: 254
            RolapConnection.execute(Query) line: 597
            CmdRunner.runQuery(String, boolean) line: 566
            CmdRunner.execute(String) line: 543
            CmdRunner.executeMdxCmd(String) line: 2243
            CmdRunner.commandLoop(Reader, boolean) line: 872
            CmdRunner.commandLoop(File) line: 750
            CmdRunner.main(String[]) line: 2397

   FunUtil.java

  public static Member[] getNonEmptyMemberChildren(
        Evaluator evaluator,
        Member member)
    {
        SchemaReader sr = evaluator.getSchemaReader();
        if (evaluator.isNonEmpty()) {
            return sr.getMemberChildren(member, evaluator);
        } else {
            return sr.getMemberChildren(member);
        }
    }




More information about the Mondrian mailing list