Group table and create measure based on parameter from different rows - powerbi

bit new to dax and I am struggling in creating a formula.
So I need to write a mathematical calculation which =+(E4+Mx6)/2*33 for the East Silo on the same date and time only.
So the first one would be 07/11/2022 4:30 am calculation (4+4)/2*33
I tried doing the calculation but i couldn't figure out how to calculate based on the same date field

You can do it in Power Query
Mark your Parameter and Value columns
Transform - Pivot them
Add custom column from the new [E4] and [Mx6] columns
M-code should look like this:
#"Pivoted Column" = Table.Pivot(
#"Changed Type", List.Distinct(#"Changed Type"[Parameter]), "Parameter", "Value", List.Sum),
#"Added Custom" = Table.AddColumn(
#"Pivoted Column", "Custom", each ([E4]+[Mx6]) / 2 * 33)

If you want to solve it in DAX, use this measure:
Math =
VAR tbl =
SUMMARIZE(
'Table',
'Table'[Datetime],
'Table'[Silo],
"E4", CALCULATE(
SUM('Table'[Value]),
'Table'[Parameter] = "E4"
),
"Mx6", CALCULATE(
SUM('Table'[Value]),
'Table'[Parameter] = "Mx6"
)
)
RETURN
SUMX(
tbl,
([E4] + [Mx6]) / 2 * 33
)

Related

7 day rolling sum not working on Power BI

I need your help. I'm working on a Power BI project and I'd like to create a Measure that calculates the 7 day rolling sum of my number of sales.
I have a table with several columns. In one of these columns, I have the number of sales per day.
My DAX measure is supposed to sum the number of sales for the day and the 6 days before. And this process is repeated for each date.
The problem is that my code doesn't work. Here's what I have:
Actual Orders - 7DR =
VAR CurrentRow = SELECTEDVALUE(Table[Date])
RETURN
CALCULATE(SUM(Table[Sales]), DATESINPERIOD(Table[Date], CurrentRow, -6, DAY))
The problem is that I also have an Excel spreadsheet with the same calculations made with a simple SUM and my results are not the same.
Do you guys have any idea why it's not working?
Thank you.
Other than perhaps an off-by-one error, that measure looks fine. With this table
let
Days = List.Dates(#date(2023,1,1),20,#duration(1, 0, 0, 0)),
#"Converted to Table" = Table.FromList(Days, Splitter.SplitByNothing(), null, null, ExtraValues.Error),
#"Renamed Columns" = Table.RenameColumns(#"Converted to Table",{{"Column1", "Date"}}),
#"Inserted Month" = Table.AddColumn(#"Renamed Columns", "Sales", each 1, Int64.Type),
#"Changed Type" = Table.TransformColumnTypes(#"Inserted Month",{{"Date", type date}})
in
#"Changed Type"
and this measure
Actual Orders - 7DR =
VAR CurrentRow = SELECTEDVALUE('Table'[Date])
RETURN
CALCULATE(SUM('Table'[Sales]), DATESINPERIOD('Table'[Date], CurrentRow, -7, DAY))
You get this
Check this one out:
7 day rolling sum =
VAR __LAST_DATE =
LASTDATE('Table'[Date])
RETURN
CALCULATE(
SUM('Table'[Sales]),
DATESBETWEEN('Table'[Date], DATEADD(__LAST_DATE, -6, DAY), __LAST_DATE)
)

Microsoft Power BI - DAX - develop a dataset using variables - NATURALJOIN, GENERATE, GENERATEALL

I have a Power BI Desktop file. I am developing a Calculated Table (CT) in DAX language.
I am using a number of manipulations inside to develop this CT (similar to what I do in a T-SQL stored procedure). I have the source as an excel file here.
I develop a number of variables within this DAX query. Ignore any relationships between the tables, since these are variables.
I have the below variable (a table) called VAR_SourceData. Please see the image file below:
It has 4 cities - NYC, LON, LA, SYD. It has 5 different combinations of City-Product.
Each City may have one or more Products.
A combination of a City-Product will have only one unique Quantity (always),
regardless of the year.
For example, SYD and PineApple has 12 as its Quantity always, on the other hand SYD and Grapes has a Quantity of 11 always. (This is regardless of the Year).
A combination of City-Product may or may not have Price for all the years.
For example, LON-Orange has Price for 2020 and 2019 only, on the other hand
LA-Mango has Price for 2019 and 2015 only.
I have a master table (VAR_ReferenceYearLookup) with all the possible years. It has 9 years (2022-2014), in descending order.
I need the desired output of the table VAR_Desired_Output:
I explain the VAR_Desired_Output table as follows:
The table would have every possible combination of City-Product, with a fixed Quantity. The City, Product, Quantity are independent of the Year. However, the Price depends on the Year. If there is no data for Price in a year in the VAR_SourceData table, the VAR_Desired_Output table must show blank.
My desired output must have all the years (2022-2014 (in descending order, preferably)) for every possible combination of City-Product, with the fixed Quantity; the Quantity depends on the City-Product combination, but not on the Year. If the Price for a Year is not available in the VAR_SourceData table, the VAR_Desired_Output table must show blank.
Hence every City-Product combination must have exactly 9 years, with a fixed Quantity always.
I have 5 different combinations of City-Product, hence the VAR_Desired_Output table has 45 rows.
I tried with NATURALINNERJOIN, NATURALLEFTOUTERJOIN, GENERATE etc. But am not able to solve this. I need this as a DAX solution, NOT in Power Query (my table has a number of Calculated Columns).
Can anyone help me achieve my goal?
You can add some power query steps to your table VAR_SourceData to achieve the required output. Try to add these below steps in the Advance Query Editor window of your table-
Note: change the previous step name accordingly in the first below step
let
//your previous existing steps,
#"Added Custom" = Table.AddColumn(#"previous step name", "Custom", each List.Sort(
List.Numbers(
List.Min(VAR_ReferenceYearLookup[Year_LKP]),
List.Max(VAR_ReferenceYearLookup[Year_LKP])
- List.Min(VAR_ReferenceYearLookup[Year_LKP]) + 1
),
Order.Descending
)),
#"Expanded Custom" = Table.ExpandListColumn(#"Added Custom", "Custom"),
#"Added Custom1" = Table.AddColumn(#"Expanded Custom", "Price_new", each if [Year]=[Custom] then [Price] else null),
#"Added Custom2" = Table.AddColumn(#"Added Custom1", "Quantity_new", each if [Year] = [Custom] then [Quantity] else null),
#"Removed Columns" = Table.RemoveColumns(#"Added Custom2",{"Year", "Price", "Quantity"}),
#"Renamed Columns" = Table.RenameColumns(#"Removed Columns",{{"Custom", "Year"}, {"Price_new", "Price"}, {"Quantity_new", "Quantity"}}),
#"Grouped Rows" = Table.Group(#"Renamed Columns", {"City", "Product", "Year"}, {{"Price", each List.Max([Price]), type nullable number}, {"Quantity", each List.Max([Quantity]), type nullable number}})
in
#"Grouped Rows"
Output-
As mentioned, I need a DAX based solution, not in Power Query.
I assume that the 2 variables (VAR_SourceData, VAR_ReferenceYearLookup) are tables, and have this code below:
DesiredOutput_CT =
VAR src = DISTINCT(
SELECTCOLUMNS(
VAR_SourceData,
"City", [City],
"Product", [Product],
"Quantity", [Quantity]
)
)
VAR cj = CROSSJOIN(src, VAR_ReferenceYearLookup)
VAR t1 = SELECTCOLUMNS(
cj,
"Concat", [City] & "-" & [Product] & "-" & [Year_LKP],
"City", [City],
"Product", [Product],
"Quantity", [Quantity],
"Year", [Year_LKP]
)
VAR t2 = SELECTCOLUMNS(
VAR_SourceData,
"Concat", [City] & "-" & [Product] & "-" & [Year],
"Price", [Price]
)
VAR t3 = SELECTCOLUMNS(
t1,
"Concat", [Concat] & "Z",
"City", [City],
"Product", [Product],
"Quantity", [Quantity],
"Year", [Year]
)
VAR t4 = SELECTCOLUMNS(
t2,
"Concat", [Concat] & "Z",
"Price", [Price]
)
VAR t5 = NATURALLEFTOUTERJOIN(t3,t4)
VAR t6 = SELECTCOLUMNS(
t5,
"City", [City],
"Product", [Product],
"Quantity", [Quantity],
"Price", [Price],
"Year", [Year]
)
RETURN t6

how to create a DAX measure / power query process / which returns a value from another row, which has the same date & time

Please find below links to the Fact table and the overview of all tables. I would like to create a DAX measure, or new column in the Fact table ("transactions"), where:
The currency is NOT equal to EUR (e.g. "BTC"),
Giving the value equal to a opposite value of "amount", as given in the row with EUR as currency (e.g. +5. Positive for negative and vice versa),
Where the date and time of the two rows (EUR and non-EUR) have the same values (e.g. 03/11/2021 and 12:28:06)
The "type" = "trade",
In all other cases, I think it would be best to give a value of 0.
In my Fact table screenshot, I manually added the EUR_amt column in Excel to show what I would like to create
I think it's also possible to add the column, then group by time and date, such that the rows with EUR as currency with EUR_amt being 0, would be removed. All using power query. That would be even better.
(The "Currencies" table just uses the distinct values of the "currency" column in the "transactions" table, via PowerQuery. Not relevant for this question I think)
Many thanks in advance!
-YK
Fact table "transactions"
Overview of tables
Calculated Column:
EUR_amt =
IF (
OR ( transactions[type] <> "trade", transactions[currency] = "EUR" ),
0,
- LOOKUPVALUE (
transactions[amount],
transactions[Date], transactions[Date],
transactions[Time], transactions[Time],
transactions[currency], "EUR",
0
)
)
Here's one way to do this using just Power Query and the Advanced Editor
Group by data and time
Generate a custom column for each subtable based on your rules
Expand the subtables, remove those with "0", and re-order the columns
let
Source = Excel.CurrentWorkbook(){[Name="Table1"]}[Content],
#"Changed Type" = Table.TransformColumnTypes(Source,{{"type", type text}, {"currency", type text}, {"Date", type date}, {"Time", type time}, {"amount", type number}}),
//Group by Date and Time
#"Grouped Rows" = Table.Group(#"Changed Type", {"Date", "Time"}, {
//Add the Eur amt column to the grouped table
{"EUR_amt", (t)=>let
//determine relevant euro amt for each sub table
eur= t[amount]{List.PositionOf(t[currency],"EUR")},
//add the column to each subtable basaed on conditions
addCol = Table.AddColumn(t, "EUR_amt",
each if [type]= "trade" and [currency]<>"EUR" then -eur else 0)
in
addCol}}),
//Expand the new table
//Filter out the 0's
//reorder the columns
#"Expanded EUR_amt" = Table.ExpandTableColumn(#"Grouped Rows", "EUR_amt", {"type", "currency", "amount", "EUR_amt"}, {"type", "currency", "amount", "EUR_amt"}),
#"Filtered Rows" = Table.SelectRows(#"Expanded EUR_amt", each ([EUR_amt] <> 0)),
#"Reordered Columns" = Table.ReorderColumns(#"Filtered Rows",{"type", "currency", "Date", "Time", "amount", "EUR_amt"})
in
#"Reordered Columns"

SUMX over table variable breaks when adding relationships to underlying table

Environment
I have created the two queries in Power Query
"Demo"
let
Source = Table.FromList(List.Random(1000, 20200427),Splitter.SplitByNothing()),
#"Changed Type" = Table.TransformColumnTypes(Source,{{"Column1", type text}}),
#"Split Column by Position" = Table.SplitColumn(#"Changed Type", "Column1", Splitter.SplitTextByPositions({0, 5, 7}, false), {"Month", "Amount"}),
#"Changed Type2" = Table.TransformColumnTypes(#"Split Column by Position",{{"Month", type number}, {"Amount", type number}}),
ConvetToMonthNumber = Table.TransformColumns(#"Changed Type2",{{"Month", each Number.RoundDown( 12 * _) + 1, Int64.Type}})
in
ConvetToMonthNumber
and "MockCal"
let
Source = Table.FromList( List.Repeat({1..4},3), Splitter.SplitByNothing(),{"CalQuart"}),
#"Added Index" = Table.AddIndexColumn(Source, "Month", 1, 1)
in
#"Added Index"
and then in the model I have two bits of DAX
Running Amount =
CALCULATE(
SUM('Demo'[Amount]),
FILTER(ALL('Demo'[Month]), 'Demo'[Month] <= MAX('Demo'[Month]))
)
and
WEIRD Run total =
VAR CalcTable = SUMMARIZE(Demo,Demo[Month],"MonthlyRollingAmounts",[Running Amount])
VAR TotalAmount = SUMX(CalcTable,[MonthlyRollingAmounts])
RETURN IF(ISFILTERED(Demo[Month]), [Running Amount], TotalAmount)
With this I can produce the following visual:
This achieves the desired result: Create a measure that sums up its slices by month.
However, when I create a relationship off this table, the SUMX stops working as expected.
The question is: Why does adding this relationship change the behavior of the SUMX? It doesn't seem to me like it should matter at all. Help is appreciated, this one is really bending my brain.
The reason for this is that in your Running Amount measure you remove any filtering on 'Demo'[Month] but this does not propagate upstream to MockCal (which I'm assuming you're using as the first column in your visual).
In general, you want to do your date filtering on your calendar table instead of your fact table. Try this instead:
Running Amount =
CALCULATE(
SUM('Demo'[Amount]),
FILTER(ALL(MockCal), 'MockCal'[Month] <= MAX('MockCal'[Month]))
)
Your WEIRD Run total should be updated as well to use the calendar table.

Power BI If Blank Then Put Value

This snippet displays the chart we are looking at and it has blanks. Instead of blanks for those dates and ID's we want to show what those values are; however, the values(Rates) may not be the same for every ID or Date. (This may happen on rare occasions.)
This snippet displays the data being pulled into Power BI from excel (Just sample data). Notice that all the dates are in order, but notice that some of the ID's do not have entries for certain dates.
I want to be able to say IF(ID is blank per this date, then put Value(Rate) that is attached to this ID).
This may not be possible to do in Power BI. We have an excel spreadsheet with similar data doing what we want but we wanted to automate by using Power BI.
Any Thoughts?
Update
I have got the measures to work in my favor, however; I need to get the total of the measure: Value Or Rate measure. I do have Value Or Rate - visual totals if I can do the same thing as the Value Or Rate measure with a total that would be great.
Please see the updated screen screenshots below.
Visual with fields
Relationships
As a measure, you could do something like below. I'm assuming that you have a model as follows:
Fact: (Date, ID, Value)
DimDate: (Date, ...)
Rates: (ID, Rate)
Dim: (ID, ...)
With these tables you'd have relationships as below:
Dim -1:N-> Fact
Dim <-1:1-> Rates
DimDate -1:N-> Fact
With the model above, you could then build a visual of:
Rows: DimDate[Date]
Columns: Dim[ID]
Values: [Value Or Rate Measure]
Value = SUM ( 'Fact'[Value] )
Rate = SUM ( 'Rates'[Rate] )
Value Or Rate Measure =
VAR Value = [Value]
RETURN
IF ( ISBLANK ( Value ), [Rate], Value )
This might not do what you want for totals - you didn't specify. So if you need visual totals you might try the following:
Value or Rate - visual totals =
SUMX (
CROSSJOIN ( VALUES ( 'Dim'[ID] ), VALUES ( 'DimDate'[Date] ) ),
[Value Or Rate Measure]
)
You could also handle this in Power Query M, assuming you have the same tables I've described above. I'm assuming each table has an associated query of the same name.
let
Source = Table.AddColumn(Dim, "Date", each DimDate[Date]),
#"Expanded Date" = Table.ExpandListColumn(Source, "Date"),
#"Merged Queries" = Table.NestedJoin(#"Expanded Date", {"id", "Date"}, Fact, {"ID", "Date"}, "Fact", JoinKind.LeftOuter),
#"Expanded Fact" = Table.ExpandTableColumn(#"Merged Queries", "Fact", {"Value"}, {"Value"}),
#"Merged Queries1" = Table.NestedJoin(#"Expanded Fact", {"id"}, Rates, {"ID"}, "Rates", JoinKind.LeftOuter),
#"Expanded Rates" = Table.ExpandTableColumn(#"Merged Queries1", "Rates", {"Rate"}, {"Rate"}),
#"Added Custom" = Table.AddColumn(#"Expanded Rates", "Value Or Rate", each if [Value] = null then [Rate] else [Value]),
#"Removed Columns" = Table.RemoveColumns(#"Added Custom",{"Value", "Rate"})
in
#"Removed Columns"
Here, we're doing something similar, but at a table level, instead of as a measure. We crossjoin Dim[ID] and DimDate[Date] to get a dense table of all date and ID combinations. Then we left join the original Fact table and the Rates table. Then we add a column that takes [Value] if it exists, or [Rate] if [Value] is null.