5

Chris Web からの投稿に続いて、顧客からの最後の購入をすばやく見つける方法を探しています。

次のような MDX ステートメントを使用します。

WITH FUNCTION previous_buys() AS tail( nonempty({NULL:[Time].[Time].currentmember.prevmember} ,[measures].[sales amt]),1)
MEMBER [last buy] as previous_buys().(0).key

select [measures].[last buy] on 0
,      [Customers].[Customers].[name].members on 1
from [Store Sales]
where [Time].[Time].[day].&[2015-12-20T00:00:00.000]

これは期待どおりですが、非常に時間がかかります。このクエリを何らかの方法で高速化する簡単な方法はありますか。icCube は Microsoft MDX とは多少異なるため、Chris Web のソリューションをコピーすることはできません。

何か案は?

4

2 に答える 2

2

このソリューションで発生する主な問題は、{NULL:[Time].[Time].currentmember.prevmember} カウントのメンバーを評価しているため、スケーラビリティです。

私は、Head 関数で Reverse を使用するとセット全体が評価されないと考えましたが、Empty 関数の現在の実装はセットを「実体化」します。これは、すべてのメンバーを評価していることを意味します。まだ有効な解決策ではありません。

別のよりエレガントな解決策は、再帰関数を使用することです。これにより、評価されるメンバーの数が大幅に削減されます。

WITH 
  FUNCTION previous_buys(t_) AS IIF( (t_,[Measures].[Amount]) = NULL,  previous_buys(t_.prevMember), t_ )
  MEMBER [last buy] as previous_buys( [Time].[Calendar].current).name

SELECT 
  [measures].[last buy] on 0,
  [Customers].[Geography].[Region]  on 1
FROM [Sales]
WHERE [Time].[Calendar].[Year].[2006].[Q1 2006].[Jan 2006].[8 Jan 2006]

空の日付がたくさんある場合は、アルゴリズムを少し複雑にして、空さをチェックするために月レベルに下げることができます。これは、1 日バージョンの 30/31 ではなく、1 回の反復で 1 か月を評価します。


最後で桁違いに速いのは、icCube の集約エンジンを利用することです。ここで必要なのは、存在する最後の日を返すメジャーです。

アイデアは、日付を入力値として、最大値を集計方法としてメジャーを追加することです。次に、この新しいメジャーを使用して、セットで eval (サブキューブをキャッシュしているため重要) を使用します。

于 2016-01-24T11:01:48.467 に答える