MDX query picking columns on different condition - sql

As shown in the below query,
SELECT
{[Measures].[Internet Sales Amount] } ON COLUMNS
,{([Product].[City].[City].ALLMEMBERS)} ON ROWS
FROM [Adventure Works]
Where ([Promotions].[City].&[Seattle],[Geography].[State-Province].&[WA]&[US])
This will list all the Product City names in row-wise and the column sales amount. Now I have to fetch the same column based on different City and State-Provine Name. So for that, I can repeat the query like this
SELECT
{[Measures].[Internet Sales Amount] } ON COLUMNS
,{([Product].[City].[City].ALLMEMBERS)} ON ROWS
FROM [Adventure Works]
Where ([Promotions].[City].&[LA],[Geography].[State-Province].&[CA]&[US])
Now I have these two queries returning same Product City names, but Two sales amount columns based on different conditions. I want to join these results like below
SELECT
{
[Measures].[Internet Sales Amount] EXISTS ([Promotions].[City].&[Seattle],
[Geography].[State-Province].&[WA]&[US]),
[Measures].[Internet Sales Amount] EXISTS ([Promotions].[City].&[LA],
[Geography].[State-Province].&[CA]&[US])
} ON COLUMNS
,{([Product].[City].[City].ALLMEMBERS)} ON ROWS
FROM [Adventure Works];
Now, this query should produce a single result with Product City names as rows and Col1 and Col2 of Internet Sales amount based on different conditions. But the problem is, the last query is giving me an error
"Parser: The syntax for 'Exists' is incorrect."
I am new to MDX, could someone please help me on how to join these results?

I was able to solve this problem based on the solution described here!
to-join-2-mdx-queries-with-same-hierarchy

Related

Simple Calculated Member Running for Forever - MDX

I am facing very strange issue with MDX (SSAS 2014), on which simplest calculated member is taking forever to execute. Could someone please help me to understand why i am facing this issue. If i not use calculated member everything works fast and result comes in seconds. When i remove Producer attribute, query performances well.
Below is the complete query.
WITH
MEMBER Measures.AsOfDate AS ("[Policy Effective Date].[Year-Month].[Date].&[2018-01-04T00:00:00]")
MEMBER Measures.YTDPremium AS AGGREGATE (YTD(STRTOMEMBER(Measures.AsOfDate)), [Measures].[Written Premium])
SELECT NON EMPTY
{
Measures.YTDPremium
} ON COLUMNS, NON EMPTY
{
(
[Program].[Program Name].[Program Name]
,[Insuring Company].[Insuring Company Name].[Insuring Company Name]
,[Line Of Business].[Line Of Business].[Line Of Business]
,[Producer].[Producer Name].[Producer Name]
)
} ON ROWS
FROM [Premium]
Try understand what the following part does in your query
NON EMPTY { ( [Program].[Program Name].[Program Name]
,[Insuring Company].[Insuring Company Name].[Insuring Company Name]
,[Line Of Business].[Line Of Business].[Line Of Business]
,[Producer].[Producer Name].[Producer Name]
) } ON ROWS
In the above MDX you are telling the server to take a cross product of all values of "Programs", "Line Of Business" and "Producer Name". So lets say you have 4 values of programs , 3 values of line of business and 2 values of producer name. The total combinations are 4*3*2=24
Now the "Non empty" removes any combinations that are not present in your dataset. This is done by removing all rows that have "Null" value in column value.
Your measure is returning value irrespective if that combination exists or not. You can modify your Calculatedmeasure to return value only in the case if the combination is valid. This can be achived by checking an actual measure for that combination
Edit: based the below example is based on the comment
In the below example i am trying to get the internet sales amount categories and components
select
{ [Measures].[Internet Sales Amount] }
on columns,
(
[Product].[Category].[Category],
[Customer].[Country].[Country]
)
on rows
from [Adventure Works]
Result
Now add "Non empty" to the query and observe the results.
Results
Now lets add calculted measure that returns "hello". Notice how the non empty clause is ineffective.
Now modify the code make the calculated measure check other measures for null
with member measures.t as
case when [Measures].[Internet Sales Amount] = null then null else "hello" end
select
{ [Measures].[Internet Sales Amount] ,measures.t }
on columns,
non empty
(
[Product].[Category].[Category],
[Customer].[Country].[Country]
)
on rows
from [Adventure Works]
Result
The bottom line: Because of cross product your result is so huge that SSAS is having hard time handling it.

Can we apply filter on measures in where condition?

enter image description here
select {[Measures].Allmembers} on columns,[Dim Customer].Allmembers on Rows from [Rightdata Db] where [Measures].[Quantity].&[43]
when i execute the above query, I get the exception below:
Query (1, 97) The '&[43]' member was not found in the cube when the
string, [Measures].[Quantity].&[43], was parsed.
Why am i not able to apply filter on measures using where condition?
You dont filter Measure in this way. Take a look at the sample below
select {[Measures].[Internet Sales Amount],[Measures].[Internet Order Quantity]} on columns,
{
filter([Product].[Subcategory].[Subcategory],[Measures].[Internet Sales Amount]>10000)
}
on rows
from
[Adventure Works]

Mondrian MDX - Filter Not Applying to Multiple Members Query

We currently have a query that shows the value of total quantity, or sales across store locations and departments, I intersect the quantity sold aggregated measure against locations, and the results are fine.
When we try to filter by total qty > 500, I am only seeing the sum of quantity evaluated by the location's value, not grouped by location and department.
HAVING is not seemingly supported, and if I include a where filter at the bottom, there is an issue with the same family/members being used multiple times and it's not allowed.
SELECT
{HEAD([dim_productfamily.hier_productfamily].[lvl_department].Members, 5)}
ON ROWS,
FILTER
(
{HEAD([dim_locations.hier_locations].[lvl_location].Members, 5) * [Measures].[total_qty]},
[Measures].[total_qty] > 500
)
ON COLUMNS
FROM
[sales_daily]
WHERE
{[dim_date.hier_date].[lvl_date].[20170521] : [dim_date.hier_date].[lvl_date].[20170730] }
The above query returns fine, but I get values that I've tested only really compare against the location sum(total_qty).
EDIT for Different Grouping
I tried using the below query, which seems to work. I think the way we render a table is improper in this case, as the output does seem to work fine.
SELECT
FILTER
(
{HEAD([dim_productfamily.hier_productfamily].[lvl_department].Members, 5) * HEAD([dim_locations.hier_locations].[lvl_location].Members, 5)},
[Measures].[total_qty] > 26
)
ON ROWS,
[Measures].[total_qty]
ON COLUMNS
FROM
[sales_daily]
WHERE
{[dim_date.hier_date].[lvl_date].[20170521] : [dim_date.hier_date].[lvl_date].[20170730] }
Is this what you were thinking?
The issue is that in your filter you really have not grouped by location and department. You have only grouped by location. An easy fix is the you bring both location and product on the same axis and that the measure on the oposite axis. Then filter it. It would work.
Looking at the problem again, you can query it in the below manner. This will let you use the orignal grouping.
WITH
MEMBER [Measures].[Data Type3] AS ([Geography].[Country].CurrentMember,[Product].[Product].CurrentMember,[Measures].[Reseller Sales Amount])
SELECT
FILTER
(
{[Product].[Product].Members}
,[Measures].[Reseller Sales Amount] > 2000
)
ON rows,
FILTER
(
([Geography].[Country].members, {[Measures].[Reseller Sales Amount]
,[Measures].[Data Type3]}),
[Measures].[Reseller Sales Amount] > 2000
)
ON columns
FROM
[Adventure Works]

MDX Record Count

Can any one tell me how to get the record count that is a result of a MDX query?I have tried various methods and I haven't really got a solution for that.I am a beginner in MDX queries.
WITH
MEMBER [Measures].[amount] as
COUNT(
[your_dimension].[your_dimension_property].Members
)
SELECT {[Measures].[amount]} ON COLUMNS
FROM [your_awesome_cube]
A code like this will return to you the amount of members in your dimension, the COUNT method have this syntax
Count(Set_Expression [ , ( EXCLUDEEMPTY | INCLUDEEMPTY ) ] )
so you can do a lot of things, like filter your search
Create a measure in the cube that is a count or distinct count.
1) open the cube
2) Right click on the fact table on which that measure sits
3) Select New Measure...
4) Dropdown the list and select the aggregation
5) In the source column section, select the column you want the aggregation on (if u cant find it, click on show all columns on the bottom- this depends on what you are aggregating)
with member
Measures.Counts as
[your_dimension].[your_dimension_property].Children.COUNT
select Measures.Counts on 0
FROM [your_awesome_cube]
When you say record count, you basicly are saying the valid combinations of your row axis.
Lets take a basic example, the query returns 3637 rows, of which 1 row is parctically the column name row.
select [Measures].[Sales Amount] on columns,
(
[Customer].[Country].[Country],
[Product].[Product].[Product]
) on rows
from [Adventure Works]
Now to get the row count without running the query, lets put the combinations in count function and put the count function in a runtime measure
This Returns 3636 row.
with member [Measures].[rowCount]
as
count(([Customer].[Country].[Country],[Product].[Product].[Product]))
select [Measures].[rowCount] on columns from [Adventure Works]
Notice I have not eleminated the null combinations on rows. Lets do that next
The query returns 2101 rows , again one row from column headers.
select [Measures].[Sales Amount] on columns,
non empty
(
[Customer].[Country].[Country],
[Product].[Product].[Product]
) on rows
from [Adventure Works]
Now lets count the rows
This returns 2100 rows.
with member [Measures].[rowCount]
as
count(nonempty(( [Customer].[Country].[Country],[Product].[Product].[Product])
,{[Measures].[Sales Amount]}
))
select [Measures].[rowCount]
on columns from [Adventure Works]
Till now we had measure from just one measure group, now lets try with multiple measure groups.
select {[Measures].[Sales Amount],[Measures].[Internet Sales Amount]} on columns,
non empty
(
[Customer].[Country].[Country],
[Product].[Product].[Product]
) on rows
from [Adventure Works]
//Cell set consists of 2101 rows and 3 columns.
//Wrong way
with member [Measures].[rowCount]
as
count(nonempty(( [Customer].[Country].[Country],[Product].[Product].[Product])
,{[Measures].[Internet Sales Amount]}
))
select [Measures].[rowCount] on columns from [Adventure Works]
//935
//Right way
with member [Measures].[rowCount]
as
count(nonempty(( [Customer].[Country].[Country],[Product].[Product].[Product])
,{[Measures].[Sales Amount],[Measures].[Internet Sales Amount]}
))
select [Measures].[rowCount]
on columns from [Adventure Works]
///2100
Notice when we use just a single measure the result may not be correct . If the measure we use has a null value then the combination would be removed. Where as in our rows the other measure will ensure that the combination appears.
Now Lets add a filter to the picture.
select {[Measures].[Sales Amount],[Measures].[Internet Sales Amount]} on columns,
non empty
filter(
(
[Customer].[Country].[Country],
[Product].[Product].[Product]
)
,[Measures].[Internet Sales Amount]>5000) on rows
from [Adventure Works]
//Cell set consists of 586 rows and 3 columns.
//Wrong way
with member [Measures].[rowCount]
as
count(nonempty(( [Customer].[Country].[Country],[Product].[Product].[Product])
,{[Measures].[Sales Amount],[Measures].[Internet Sales Amount]}
))
select [Measures].[rowCount]
on columns from [Adventure Works]
//2100
//Right way
with member [Measures].[rowCount]
as
count(nonempty(
filter(([Customer].[Country].[Country],[Product].[Product].[Product]),[Measures].[Internet Sales Amount]>5000)
,{[Measures].[Sales Amount],[Measures].[Internet Sales Amount]}
))
select [Measures].[rowCount]
on columns from [Adventure Works]
///585
Again till i gave the RowCount measure the exact senario that I have on my row axis it fails.

Select kpi with month on columns

I want to get two plant's oee per month in a specific year (2013), probably it's pretty trivial but I don't know how to do it:
with member [Measures].[OEE] as 'OEE'
select
{
[Equipment].[Plant Hierarchy].[Group].[DEMO_PLANT],
[Equipment].[Plant Hierarchy].[Group].[DEMO_PLANT2]
} on columns,
{
[Time].[Month]
} on rows
from ExpertPlan
where [Time].[Year].&[2013-01-01T00:00:00]
the select is ok (plants on columns and months on rows), but i'm not sure about the "with" usage to get the values be the [Measures].[OEE]
With is for custom calculated members and custom sets.
Add your measure to the slicer (WHERE clause)
SELECT
{
[Equipment].[Plant Hierarchy].[Group].[DEMO_PLANT]
,[Equipment].[Plant Hierarchy].[Group].[DEMO_PLANT2]
} ON COLUMNS
,{[Time].[Month]} ON ROWS
FROM ExpertPlan
WHERE
(
[Time].[Year].&[2013-01-01T00:00:00]
,[Measures].[OEE]
);
Here are a couple of prototyped ways of approaching this in AdvWrks cube:
SELECT
[Customer].[Country].&[United States] ON COLUMNS
,[Date].[Calendar].[Month] ON ROWS
FROM [Adventure Works]
WHERE
(
[Date].[Calendar Year].&[2007]
,[Measures].[Internet Sales Amount]
);
SELECT
[Customer].[Country].&[United States] ON COLUMNS
,Descendants
(
[Date].[Calendar].[Calendar Year].&[2007]
,[Date].[Calendar].[Month]
) ON ROWS
FROM [Adventure Works]
WHERE
[Measures].[Internet Sales Amount];
Both of the above result in this result cell set:
Adding on to the other answer, you can also employ a subselect.
SELECT
{
[Equipment].[Plant Hierarchy].[Group].[DEMO_PLANT]
,[Equipment].[Plant Hierarchy].[Group].[DEMO_PLANT2]
} ON COLUMNS
,{[Time].[Month]} ON ROWS
FROM
(
SELECT [Time].[Year].&[2013-01-01T00:00:00] ON 0
FROM [ExpertPlan]
)
WHERE
{[Measures].[OEE]}
In MDX, WHERE is the 3rd axis, although it is not too apparent. Think it to be like excel, where you have the rows, columns and values. You can put the hierarchies(attribute) on any of the axes([Measures] also behaves like any regular hierarchy). It will just change the way your final output will look like.