MDX: count number of members selected in filter - ssas

I have one dimension that I want to put into filter, and created calculated member that should dynamically show number of selected members from the dimension.
The dimension does not have an All member.
So this is my attempt
with member [Measures].[Count1] as count(existing(([MyDimension].[MyDimensionHierarchy].members)))
select [Measures].[Count1] on 0
from [MyCube] -- gives me 1
and this one will give me 2 which is correct:
with member [Measures].[Count1] as count(existing(([MyDimension].[MyDimensionHierarchy].members)))
select [Measures].[Count1] on 0
from [MyCube]
where ({[MyDimension].[MyDimensionHierarchy].[Member1], [MyDimension].[MyDimensionHierarchy].[Member2]})
But, the problem is that when I create calculated member with the formula above, and drag Count1 to the Excel pivot table, and drag MyDimension as filter, and when I do multi-select of the dimension members, I want the count to dynamically change as I change number of members that are selected.
But Count1 always stays equal to 1.

In a meantime I have found an answer:
The query that I wrote in the question actually is not the query that Excel pivot table sends to the cube. Excel pivot table generates query like this:
SELECT FROM (SELECT ({[MyDimension].[MyDimensionHierarchy].[Member1],[MyDimension].[MyDimensionHierarchy].[Member2]}) ON COLUMNS
FROM [MyCube])
WHERE ([Measures].[Count1])
The way this should be done is by using dynamic set that contains filtered members:
create dynamic set [SelectedMembers] as existing( [MyDimension].[MyDimensionHierarchy].members )
And then:
create member Measures.SelectedMembersCount as count([SelectedMembers])
So this set dynamically changes as different members are selected in the filter and SelectedMembersCount is dynamically changed along the way.

Related

using a named set in a calculated member

I have a calculated field (getting a count) and a named set (defines a key) which I want to use in a new calculated member and return the count based on when the key is defined in that set.
So far i have tried this:
([Measures].[Person ID Distinct Count], [SET]) and
([Measures].[Person ID Distinct Count], {[SET]})
Just on a side note, I for this discount count in 2 steps:
I first did a count on the table using new measure... option from cube structure pane, then used it in a calculation to define the year of count i want. And now I am here. My mdx above didn't work but however in the browser i can pull the count (where its filtered by year) and use the set as a slice and it works fine. But I want this defined in a calculation.
This signifies a tuple (....)
A tuple is made up of members - so a set cannot be used as an argument.
You need to aggregate your set separately to create a member:
Aggregate([SET])
The memeber can then be used in the tuple you mention:
([Measures].[Person ID Distinct Count], [SomeDim].[SomeHierarchy].[All].[AggregatedSET])

SSAS new measure with a fixed dimension value

I am trying to create a measure in SSAS 2012 that looks something like that in MDX:
SELECT
{[Measures].[DWH FACT Events Count]} ON COLUMNS
FROM [27BI]
WHERE
[DWH DIM Event Name].[Event Name].&[wizard_done-button_click];
This gives me the result of counting rows (DWH FACT Events Count) when the Event Name is fixated to be "wizard_done-button_click".
I want this measure to update on each slice of the cube (i.e choose a country). While this query works, I don't know how to get it to become an actual measure.
One solution I saw was to create a Calculation:
CREATE MEMBER CURRENTCUBE.[Measures].[WizardDone]
AS
(
[Measures].[DWH FACT Events Count] ,
[DWH DIM Event Name].[Event Name].&[wizard_done-button_click]
)
This calculated member gives me the result I want, but it doesn't update when I browse the cube and try to slice it by different dimensions.

MDX - Is it possible to have two unrelated dimension members in one row?

I need to create the table of the following structure in MDX (to be used in SSRS report):
For that I have 2 dimensions and one measure:
Option dimension, with option type and option value attributes
Standard dimension, with IsStandard flag
Price measure
In first column I need to show all option type attributes,
in second all value attributes where IsStandard flag is set to [Y],
in third values chosen by user in parameters and
in fourth prices for components selected by user.
Is it possible to do the above in single MDX? Or will I be better off creating 2 distinct queries and creating 2 tables for them?
EDIT: Since my updates won't fit into the comment, I will add some thoughts here.
EXISTS function from answer below does not filter the result set, I don't get standard values but all possible values concatenated. When I issue the following code:
SELECT
[Measures].[Price] ON 0,
NON EMPTY [Option].[Option Type].children
*
[Option].[Option Value].children ON 1
FROM [Cube]
WHERE
(
[Standard].[IsStandard].&[Y],
[Configurations].[Configuration].&[conf1]
)
It returns the default values correctly, but if I use
SELECT
[Measures].[Price] ON 0,
[Option].[Option Type].children
*
EXISTS(
[Option].[Option Value].[Option Value].members
,([Standard].[IsStandard].&[Y],[Configurations].[Configuration].&[conf1])
) ON 1
FROM [Cube]
It does not filter the results.
If you can accept a slightly different order of columns, then this can be done in MDX, using a calculated measure which is actually a string (as you want to see a list of attributes values in column). This avoids having the same attribute twice in the rows:
WITH Member Measures.[Standard Value] AS
Generate(NonEmpty([Option].[Option Type].[Option Type].Members,
{([Standard].[IsStandard].&[Y],
Measure‌​s.[Price]
)}
),
[Option].[Option value].CurrentMember.Name,
", "
)
SELECT { Measures.[Standard Value], Measures.[Price] }
ON COLUMNS,
NON EMPTY
[Option].[Option Type].[Option Type].Members
*
{ #chosenValues } // the parameters value should be a comma separated list like "[Option].[Option value].[AMD], [Option].[Option value].[INTEL]"
ON ROWS
FROM [Your Cube]
WHERE [Configurations].[Configuration].&[conf1]
You can adapt the list separator (the last argument of the Generate function) to anything you like.
And in case there is more than one measure group that is related to the dimensions [Option], [Standard], and [Configurations], you should add the name of the measure group to use for determining the relationship as additional last parameter to the Exists, so that you and not the engine determines that. Just use the name of the measure group in either single or double quotes.
Yes it is, dimension will just be ignored. This is assuming you've all in the same schema / cube.
Note, depending on the OLAP Server you're using it's possible you've to change a flag that sends an error if you're using a dimensions that is not defined at Measure Group level.

Create dynamic calculated member based on dimensions selected ON ROWS

Is there a way to create a dynamic calculated member based on the dimension selected ON ROWS?
I have the following example with 2 dimensions [Dim1].[Dim1] and [Dim2].[Dim2], with a measure [Measures].[Measure] and a calculated member [Measures].[CalculatedMeasure]:
WITH MEMBER [Measures].[CalculatedMeasure] AS
IIF([Dim1].[Dim1]**.....IS SELECTED ON ROWS.........**,
[Measures].[Measure]
/
([Measures].[Measure], [Dim1].[Dim1].CurrentMember.Parent),
[Measures].[Measure]
/
([Measures].[Measure], [Dim2].[Dim2].CurrentMember.Parent))
SELECT {[Measures].[Measure],[Measures].[CalculatedMeasure]} ON COLUMNS ,
{[Dim2].[Dim2].Members)} ON ROWS
FROM [DataBase]
What I want is that when I select [Dim2].[Dim2] ON ROWS, the calculated member should be the result of
[Measures].[Measure]
/
([Measures].[Measure], [Dim2].[Dim2].CurrentMember.Parent)
ELSE
[Measures].[Measure]
/
([Measures].[Measure], [Dim1].[Dim1].CurrentMember.Parent)
Thanks
In Analysis Services, your [Dim1].[Dim1]**.....IS SELECTED ON ROWS.........** could be coded as
Axis(1).Item(0).Item(0).Hierarchy IS [Dim1].[Dim1]
if you can assume there is only one hierarchy on the rows.
Here, Axis(1) returns the rows axis as set. I am not sure if this function is supported by Pentaho/Mondrian. Then, the first Item(0) selects the first tuple of this set, and the second one returns the first member of that tuple. Finally, the Hierarchy function returns the hierarchy of a member.
To extend this to queries containing up to three hierarchies in the rows, you would write
Axis(1).Item(0).Item(0).Hierarchy IS [Dim1].[Dim1] OR
Axis(1).Item(0).Item(1).Hierarchy IS [Dim1].[Dim1] OR
Axis(1).Item(0).Item(2).Hierarchy IS [Dim1].[Dim1]

Filtering a Measure (or Removing Outliers)

Say I have a measure, foo, in a cube, and I have a reporting requirement that users want to see the following measures in a report:
total foo
total foo excluding instances where foo > 10
total foo excluding instances where foo > 30
What is the best way to handle this?
In the past, I have added Named Calculations which return NULL if foo > 10 or just foo otherwise.
I feel like there has to be a way to accomplish this in MDX (something like Filter([Measures].[foo], [Measures].[foo] > 10)), but I can't for the life of me figure anything out.
Any ideas?
The trick is that you need to apply the filter on your set, not on your measure.
For example, using the usual Microsoft 'warehouse and sales' demo cube, the following MDX will display the sales for all the stores where sales were greater than $2000.
SELECT Filter([Store].[Stores].[Store].members, [Unit Sales] > 2000) ON COLUMNS,
[Unit Sales] ON ROWS
FROM [Warehouse and Sales]
I met similar problem when use saiku (backend with Mondrain), as I haven't found any clear solution of "add filter on measure", I added it here, and that may be useful for other guy.
In Saiku3.8, you could add filter on UI: "column"->"filter"->"custom", then you may see a Filter MDX Expression.
Let's suppose we want clicks in Ad greater than 1000, then add the following line there:
[Measures].[clicks] > 1000
Save and close, then that filter will be valid for find elem with clicks greater than 1000.
The MDX likes below (suppose dt as dimension and clicks as measure, we want to find dt with clicks more than 1000)
WITH
SET [~ROWS] AS
Filter({[Dt].[dt].[dt].Members}, ([Measures].[clicks] > 1000))
SELECT
NON EMPTY {[Measures].[clicks]} ON COLUMNS,
NON EMPTY [~ROWS] ON ROWS
FROM [OfflineData]
i think you have two choices:
1- Add column to your fact(or view on data source view that is based on fact table)like:
case when unit_Price>2000 then 1
else 0
end as Unit_Price_Uper_Or_Under_10
and add a fictitious Dimension based on this columns value.
and add named query for New Dimension(say Range_Dimension in datasourceview :
select 1 as range
union all
select 0 as range
and after taht you cant used this filter like other dimension and attribute.
SELECT [Store].[Stores].[Store].members ON COLUMNS,
[Unit Sales] ON ROWS
FROM [Warehouse and Sales]
WHERE [Test_Dimension].[Range].&[1]
the problem is for every range you must add When condition and only if the range is static this solution is a good solution.
and for dynamic range it's better to formulate the range (based on disceretizing method )
2- add dimension with granularity near fact table based on fact table
for example if we have fact table with primary key Sale_id.we can add
dimension based on fact table with only one column sale_Id and in dimension Usage tab
we can relate this new dimension and measure group with relation type Fact and
after that in mdx we can use something like :
filter([dim Sale].[Sale Id].[Sale Id].members,[Measures].[Unit Price]>2000)