第17回 DAXの理解に必要となる、コンテキストとイテレーター

DAXの基本を理解するには、「コンテキスト」という概念を知る必要があります。

二つのコンテキスト

コンテキストとは、そもそも「文脈」という意味ですが、ITの世界ではプログラムが実行される状況によって違った動作をすることを指します。

ピボットテーブルを例に説明します。売上高という項目があり、得意先ごとや販売地域別に合計する場合、これらを切り口=ディメンションとして、目的に応じデータの見せ方を変化させるツールがピボットテーブルです。

つまり、同一データに対し、目的に応じて異なる計算結果をピボットテーブル上に算出する状況が「コンテキスト」だと考えると良いでしょう。

そもそもDAXは、Power Pivot for Excel(以下、パワーピボットと呼びます)で使う計算式であり関数です。

その原型のピボットテーブルは、列データを対象に、ピボットテーブの要素である「行」や「フィルター」という切り口を変えながら、目的に沿ってデータを分析し、結果をピボットテーブルに表示しているわけです。

例えば、001というIDの商品だけの売上合計を計算するという具合です。

つまり、DAXには大別して二つのコンテキストがあることになります。

それが、「行コンテキスト」と「フィルターコンテキスト」

ごく簡単に説明すると、行コンテキストは現在の行であり、フィルターコンテキストは行コンテキストに追加して適用するフィルターを指します。

簡単な事例でDAXを考える

TotalSales = SUM(Sales[SalesPQ])

このDAX式は、SUMという関数を使い、SalesというテーブルのSalesPQという列を対象に、TotalSalesという名称で売上合計を算出します。

このDAX式は、行コンテキストを有していますが、フィルターなしで計算していますのでフィルターコンテキストはありません。

DAX式は、他のDAX式で使うことができます。

ここでは、このTotalSalesというDAX式を使い、次のように定義してみます。

IdSales = CALCULATE( [TotalSales], SalesRep[ID] = “001” )

このDAX式は、CALCULATEというフィルター関数を使い、先に定義したTotalSalesという売上合計を求めるDAX式(これが、行コンテキスト)において、SalesRepテーブルのID列が“001”のデータだけ(これが、フィルターコンテキスト)を抽出します。

図表1をご覧ください。A列・B列のSalesテーブルと、D列のSalesRepテーブルのうち、ID001の分だけを抽出した結果が、F列に先に定義したDAX式のIdSalesにより3500として計算結果が表示されているのがわかります。

これは、ピボットテーブルでA列の001にフィルターした結果と同じです。

図表1IdSales = CALCULATE( [TotalSales], SalesRep[ID] = “001” )の結果

Xが目印のイテレーターという反復子

DAXでよく使うのが、SUMXなど末尾にX(エックス)のついたイテレーター(反復子)です。最大値を計算するMAXXなど、イテレーターというDAX関数はよく用います。
図表1の結果をPower PivotでIDごとに表示すると、図表2右上(F列・G列)のようになります。どのIDのIdSalesともに3500で、総計も3500になっています。これは、先のDAXで定義した際に用いたSUMによる影響です。
末尾にXのつかないSUMというDAX関数は、ファクトテーブル(ここでは、Salesテーブル)全体で集計値を計算する関数です。先の定義では、IDが001というフィルターをかけたので、001の売上合計3500をすべての行に表示しています。
これに対して、末尾にXのつくSUMXは、行ごとに計算するDAX関数です。ピボットテーブルの行ラベルにIDがある場合、IDごとに値を集計することは、ピボットテーブルを使ったことがあればわかると思います。これと同じことをSUMXのような「X」が末尾についたイテレーターが実行します。

SUMX:= CALCULATE( SUMX( Sales, (Sales[SalesPQ] ) ))

図表2 SUMX:= CALCULATE( SUMX( Sales, (Sales[SalesPQ] ) ))の結果(F列・G列の下図)

今回のポイント
・DAXには、「行コンテキスト」と「フィルターコンテキスト」の二つがある。
・SUMとSUMXでは結果が異なる。
・末尾XのDAX関数はイテレーターという反復子で、行ごとに計算する。

モダンExcel研究所

フォローお待ちしてます!

error: Content is protected !!