Power BI Rolling Total Previous Month DAX - powerbi

I am working in POWER BI and trying to calculate a DAX expression for the rolling total of the previous month. I have a filter where I select a certain month, I would like to calculate the rolling total for the previous month.
Below is the calculation that works perfectly to calculate the rolling total for the selected date range.
How can I calculate the previous months rolling total?
Rolling_Total_Current_Month = CALCULATE(
SUM(SalesInvoice[Sales])
,FILTER(ALLSELECTED(SalesInvoice), (SalesInvoice[Date]) <= MAX(SalesInvoice[Date])))
Here is a sample of my data, I have sales per day, for multiple categories, (in fact i have a couple more columns of details but this is simplified)
Date Day Amount Category
1/1/2016 1 100 A
1/1/2016 1 120 B
1/1/2016 1 90 C
1/2/2016 2 500 A
1/2/2016 2 321 B
1/2/2016 2 143 C
So far I have come up with an equation to solve the rolling total, but when I try to slice is and view the rolling total of a single category it does not work for the previous month. I just keeps the original rolling total for the previous month.
Here is the equation for the rolling total previous month that works. But does not recalculate a rolling total for the previous month once sliced based on category.
PREVIOUS_MONTH_ROLLING_TOTAL =
CALCULATE(
[Current Sales]
,FILTER(
ALL( Orders )
,Orders[MonthNumber] = MAX( Orders[MonthNumber] ) - 1
&& Orders[Day] <= MAX( Orders[Day] )
)
)

I have solved how to get the previous months rolling total.
You must do three things. First create a Month Number column in your data sheet (this is used as an integer to subtract 1 month from). You must also create a days column as well.
Then create a measure for Current Sales or whatever your value is.
Create a measure for the current month sales
Current Sales = SUM(Orders[Amount])
Then this equation.
PREVIOUS_MONTH_ROLLING_TOTAL =
CALCULATE(
[Current Sales]
,FILTER(
ALL( Orders )
,Orders[MonthNumber] = MAX( Orders[MonthNumber] ) - 1
&& Orders[Day] <= MAX( Orders[Day] )
)
)
The Idea of this equation is to be able to display the previous months rolling total on a chart with the X axis as "DAY" (so 1-31) Then you can view the current month, previous month, same period last year all on the same chart or table.

Try something along these lines:
Rolling_Total_Previous_Month =
VAR CurrentMonth = MAX(SalesInvoice[Date])
VAR PreviousMonth = EOMONTH(CurrentMonth,-1)
RETURN CALCULATE(SUM(SalesInvoice[Sales]), SalesInvoice[Date] <= PreviousMonth)

To start of, I have a data like this in a table called as Orders-
Date Amount
12/12/2017 100
12/12/2017 200
12/12/2017 300
1/1/2018 400
1/1/2018 500
I first create a calculated column called as Year & Month by using the formula:-
Year = YEAR(Orders[Date])
Month = FORMAT(Orders[Date],"mmmm")
Then I create a column called as Month Number which will be helpful for sorting when more than one year is involved in the table and as well as to Identify the Previous Months.
MonthNumber = DATEDIFF(Min(Orders[Date]),Orders[Date],MONTH)
Current Month Sales can be a measure or a Calculated column. Qn the Question, you had your answer for current month sales via a calculated column and if you want to go for a measure then something like this would work on a summary table.
Current Month Sales = SUm(Orders[Amount])
I would also create a column called as Key:-
Key = Orders[MonthNumber] & Orders[Category]
Now, for the Previous Month Sales, I would create a measure that looks for selected MonthNumber that we created.
Previous Month Sales =
Var SelectedCategory = SELECTEDVALUE(Orders[Category])
Var SelectedMonthNumberr = SELECTEDVALUE(Orders[MonthNumber]) - 1
Var ReqKey = SelectedMonthNumberr & SelectedCategory
Return
IF(ISBLANK(SelectedCategory) <> True(),
CALCULATE(SUM(Orders[Amount]),FILTER(ALL(Orders), Orders[Key] = ReqKey)),
CALCULATE(SUM(Orders[Amount]),FILTER(ALL(Orders), Orders[MonthNumber] = SelectedMonthNumberr)))
or to your Measure
PREVIOUS_MONTH_ROLLING_TOTAL =
CALCULATE(
[Current Sales]
,FILTER(
ALL( Orders )
,Orders[MonthNumber] = MAX( Orders[MonthNumber] ) - 1
&& Orders[Day] <= MAX( Orders[Day] )
)
)
You can just add another filtering item as && Orders[Category] = SELECTEDVALUE(Orders[Category]) but won't work when you don't have any categories selected or on a table or visual which doesn't have categories. So, you would need to define an if else logic here as I have quoted on my measure formula.
Do let me know, if this helps or not.

Related

Would like to do a previousquarter calculation but for the first quarter show the value without the calculation

I have dax written that returns the sales by subtracting the sales ytd by sales ytd in the previous quarter, this is to show on a pie chart or donut chart. I would like some help as I would also like to show the first quarter without the calculation.
My current dax is shown below:
Measure =
VAR RESULT = CALCULATE(
[Sale YTD],
PREVIOUSQUARTER(dimSalesDate[DATE])
)
RETURN [Sale YTD] - RESULT
my data:
quarter no sales ytd
1 50,000
2 70,000
3 150,000
4 280,000
what I want to show in a pie/donut chart
quarter no sales ytd
1 50,000 (no calculation)
2 20,000 (calculation: 70,000 - 20,000)
3 80,000 (calculation: 150,000 - 70,000)
4 130,000 (calculation: 280,000 - 150,000)
I think you may be looking for something like this:
Sales YTD Less Prior Quarter =
VAR RESULT =
IF (
SELECTEDVALUE(dimSalesDate[Quarter]) = 1,
[Sale YTD],
[Sale YTD] - CALCULATE ( [Sale YTD], PREVIOUSQUARTER ( dimSalesDate[DATE] ) )
)
RETURN
RESULT

Tracking Changes in TOP N Products from Year to Year using DAX in PowerBI

Let's say I set my slicer value to N = 3 and Year = 2021, I would like to return a table that shows which products were in the Top 3 in the selected year 2021 but not in the prior year 2020.
So if the TOP 3 products in 2021 were Bananas, Oatmeal and Chocolate, and in 2020 were Bananas, Bread, and Coffee, the result should just be Oatmeal and Chocolate. In general, the results will vary for the user-selected values of N and Year.
I've written a DAX query that does exactly this with no problem. The problem is that I can't dynamically use it in Power BI:
``` Measure Top N SKU IN =
VAR N = MAX('Popularity Slicer'[Value]) -- get max value on the popularity slicer
VAR YearSlicer = SELECTEDVALUE('L2 Top SKUs'[Year]) -- get sliced year
-- filter table on TOP N and selected Year
VAR SelectedYearTable =
CALCULATETABLE(
'L2 Top SKUs',
FILTER('L2 Top SKUs', 'L2 Top SKUs'[Popularity] <= N),
FILTER('L2 Top SKUs', 'L2 Top SKUs'[Year] = YearSlicer) -- look at the previous year
)
-- filter table on TOP N and prior Year
VAR PriorYearTable =
CALCULATETABLE(
'L2 Top SKUs',
FILTER('L2 Top SKUs', 'L2 Top SKUs'[Popularity] <= N),
FILTER('L2 Top SKUs', 'L2 Top SKUs'[Year] = YearSlicer - 1 )
)
-- get popularity measure
VAR SelectedYear =
SELECTCOLUMNS(
SelectedYearTable,
"Matnr", [Matnr],
"Year", [Year],
"Cosine", [Total Cosine Projection],
"Popularity", RANKX(SelectedYearTable, [Total Cosine Projection])
)
VAR PriorYear =
SELECTCOLUMNS(
PriorYearTable,
"Matnr", [Matnr],
"Year", [Year],
"Cosine", [Total Cosine Projection],
"Popularity", RANKX(PriorYearTable, [Total Cosine Projection])
)
-- get the intersection
VAR SKUs = EXCEPT(
SELECTCOLUMNS(
FILTER(SelectedYear, [Popularity] <= N),
"SKU",
[Matnr]
),
SELECTCOLUMNS(
FILTER(PriorYear, [Popularity] <= N),
"SKU",
[Matnr]
)
)
RETURN
SKUs```
The measure won't return the results, SKUs because it contains multiple values. I can't compute a table, however, because SELECTEDVALUE only works in measures . . . Below is a screenshot of what the query should return. Can anyone help?
Screenshot of DAX query which returns new "Most Popular" products in 2021 for N = 20 and Year = 2021
EDIT: I've since tried taking the virtual column, SKUs, and converting this into an actual measure. I did this with the following code in DAX Studio and it worked perfectly (see attached photo).
The code asks the base table 'L2 Top SKUs' if any of it's parts numbers (Matnr) are in the virtual column SKUs and returns 1 if "yes" and 0 if "no". Then, to evaluate the measure, I add it as a column to the base table and filter for [Top] = 1, which gives the correct answer. When I go to do this in PowerBI it gives some 1's and some 0's but it's not correct and it is the same exact code:
MEASURE 'L2 Top SKUs'[Top] = If(FIRSTNONBLANK('L2 Top SKUs'[Matnr], 0) IN SKUs, 1, 0)
VAR Results = ADDCOLUMNS(
SELECTCOLUMNS(
'L2 Top SKUs',
"Matnr", 'L2 Top SKUs'[Matnr]
),
"Top", [Top]
)
EVALUATE
DISTINCT(FILTER(Results, [Top] = 1))```
![Screenshot of DAX query which returns new "Most Popular" products in 2021 for N = 20 and Year = 2021][2]
[1]: https://i.stack.imgur.com/WLAHQ.png
[2]: https://i.stack.imgur.com/yt0bV.png
I found a work around for what I was trying to do, which was to calculate a table that shows the change in a measure from a previous time period. The way to do this is to have two Date tables connected in series to the primary table (or tables) and to make the relationship between them inactive. I then used two different slicers (one corresponding to each of the Date tables) which I was able to use to compare two different periods of time. The two periods are user set in this case, which is not exactly what I was thinking (I wanted the time differential to be automatically set to 1 year), but it does job.
Here's how to build it: https://www.daxpatterns.com/comparing-different-time-periods/

Calculate Number of Working Days based on a Month

Using Power Bi desktop,
I need to create a query where the result will be the current month's working days.
For example July 2021 has 22 working days and so on.
My goal for achieving this will be to be to average the number of lines processed divided into the number of working days for the current month.
Will this be possible?
You can always get the job done only by creating just a single measure and nothing else like following
_count =
COUNTX (
FILTER (
VALUES('fact'[_factDate]),
WEEKDAY ( 'fact'[_factDate], 1 ) <> 1
&& WEEKDAY ( 'fact'[_factDate], 1 ) <> 7
),
'fact'[_factDate]
)
The minimum dependency of the calculations are having a calendar table like this
Calendar_Date
Calendar_Year
Calendar_Month
1/1/2000
2000
1
first create a calculated column in you calendar table (Dates for my case) with this below code-
Column = if(
FORMAT(Dates[date],"dddd") = "Saturday"
|| FORMAT(Dates[date],"dddd") = "Sunday",
0,
1
)
now create a measure as below-
weekday = sum(Dates[Column])
now, create visual with month and new measure.

How to find day over day change in summarize table taking two columns into account

I have a summarize table that is summed by the Date and Building_Name. I am trying to figure out how to add an increase/ decrease column like my table below. I want to show if the 'total unsigned' has increased from day to day for each building.
I cannot get a formula that will take the previous days total for one building - current days # of total unsigned. Trying to get the forth column for my report. 
I can get it to work if I am just showing day over day change if I am not also trying to add the Building_name to the table.
Unsigned Prev Day =
VAR CurrentDay = SELECTEDVALUE(SummarizeTable[Day Number])
VAR CurrentMonth = SELECTEDVALUE(SummarizeTable[Month Number])
VAR MaxDayNumber = CALCULATE(MAXA(SummarizeTable[Day Number]))
Return SUMX(
FILTER(ALL(SummarizeTable),
IF( CurrentDay = 1,
SummarizeTable[Day Number] = MaxDayNumber && SummarizeTable[Month Number]= CurrentMonth-1,
SummarizeTable[Day Number] = CurrentDay -1)),
[Total Unsigned])
Edit:
Thank you for the help, you definitely put me on the right track. This is the formula I ended up using. Thank you again for the help!
Unsigned Prev Day =
VAR MostRecentDate = MAX ( 'SummarizeTable'[Date] )
RETURN
CALCULATE (
[Total Unsigned],
ALL ( 'SummarizeTable'[Date], 'SummarizeTable'[Day Number], 'SummarizeTable'[Month Number] ),
'SummarizeTable'[Date] = MostRecentDate - 1
)
This assumes that you have or can make a column, 'SummarizeTable'[Date]. If you already have month and day, this should be trivial. This solution takes advantage of the fact that DAX has well-behaved arithmetic on dates.
Additionally, you should look at building a date dimension, rather than doing all of this out of a single table. It will ultimately make your life a lot easier. There are a bunch of good date dimensions out there, but I'm partial to mine.
EDIT: Per discussion in comments the goal is to add this as a calculated column to a data table. The definition above is intended to be used as a measure.
# Increase/ Decrease =
CurrentRowDate = 'SummarizeTable'[Date]
RETURN
CALCULATE (
SUM ( 'SummarizeTable'[Total Unsigned] ),
ALLEXCEPT ( 'SummarizeTable'[Building] ),
'SummarizeTable'[Date] = CurrentRowDate - 1
)
This will add a column to 'SummarizeTable' that has the sum of [Total Unsigned] for the same value of [Building] as is on the current row and with a date 1 less than that on the current row.

Monthly sales trend in Power BI based on working days

I have daily sales data and I would like to create a measure or a column that calculates the monthly sales trend based on the average daily units sold in the month.
For example, as of 08/17/2017, we have had 12 working days this month and 360 units sold. This is an average of 30 units per day. So to calculate the trend manually, I would take 30 units/day and multiply it by the 23 total working days in the month for a trend of 690 units sold.
Here is some sample data.
EDIT: Adjusted the explanation and measure definitions based on the new info that was added to the post
You can create three measures to help you reaching your final result. In this example I'm merely splitting the measure into three parts to increase the readability. You can put it all together in a single measure if you like.
The first measure gives you the number of units sold. This is just a simple sum of units sold, since you have already added a month filter to your measures in your sample:
Sales:=SUM('SalesTable'[Items Sold])
The second measure gives you the number of working days for the filtered month up until the latest entry in your Sales Table:
WorkingDaysToDate:=
CALCULATE(
COUNTROWS('DateTable'),
FILTER(
'DateTable',
'DateTable'[Date] > CALCULATE(MAX('SalesTable'[Date]))
&& [Type] = 'Work Day'
)
)
The third measure gives you the total number of working days for the filtered month:
WorkingDays:=
CALCULATE(
COUNTROWS('DateTable'),
FILTER(
'DateTable',
[Type] = 'Work Day'
)
)
In the end you can combine the three measures to get your month trend:
MonthTrend:=DIVIDE([Sales], [WorkingDaysToDate]) * [WorkingDays]
Total Month To Date Sales
TotalMTDSales = SUM('Sales Table'[Items Sold])
Total Month To Date Work Days
TotalMTDWorkDays = CALCULATE(
COUNT('DateTable'[Date]),
FILTER(ALLSELECTED('DateTable'), 'DateTable'[Date]<=MAX('SalesTable'[Date]) &&
'DateTable'[Type] = "Work Day"))
Total Work Days
TotalWorkDays = CALCULATE(
COUNTROWS('DateTable'),
FILTER(
'DateTable',
'DateTable'[Type]= "Work Day"))
Trend = ([TotalMTDSales] / [TotalMTDWorkDays] ) * [TotalWorkDays]
Filter by Month