Forum Discussion

Anonymous's avatar
Anonymous
Not applicable
4 years ago
Solved

Adding new rows to a table based on previousday value

Hello,

 

I have a table that records the daily stocks from each user, however days in which the user did not input the stock values, I need this omitted dates to be filled by the previous day value per user per product id.

 

sample data

useridproductidvaluedate
1a       6,4338/18/2022
1b       1,8748/18/2022
1a       1,3588/22/2022
2a       1,2568/18/2022
2b       3,0508/19/2022
1b             108/23/2022
1a           4728/23/2022
2b       1,3828/23/2022
2a           1528/25/2022

 

Expected Result

useridproductidvaluedate
1a64338/18/2022
1a64338/19/2022
1a64338/20/2022
1a64338/21/2022
1a13588/22/2022
1a4728/23/2022
1a4728/24/2022
1a4728/25/2022
1b18748/18/2022
1b18748/19/2022
1b18748/20/2022
1b18748/21/2022
1b18748/22/2022
1b108/23/2022
1b108/24/2022
1b108/25/2022
2a       1,2568/18/2022
2a       1,2568/19/2022
2a       1,2568/20/2022
2a       1,2568/21/2022
2a       1,2568/22/2022
2a       1,2568/23/2022
2a       1,2568/24/2022
2a1528/25/2022
2b       3,0508/19/2022
2b       3,0508/20/2022
2b       3,0508/21/2022
2b       3,0508/22/2022
2b       1,3828/23/2022

 

Thank you Vijay_A_Verma  and Jimmy801 

  • Hi, Anonymous ;

    You could duplicate a table as TableB, then grroup by the min date , and add yestoday date column.

    Then merge column from original table and TableB,

    Last sort and fill down.

    See the working here - Open a blank query - Home - Advanced Editor - Remove everything from there and paste the below code to test.

    let
        Source = Table.FromRows(Json.Document(Binary.Decompress(Binary.FromText("dc9JCsAgDAXQqxTXgeqPqelZxEV7/0N0ULB1CGQRePwkMRpnyBx3L7k28sz3qKvTFRYwiTI6K3KkwQ/R8UUs+iKgIrQIsnVJ+K9jsmIz2qc3lbzswNOznvIBHUP7IusYNVlOCpPC0gU=", BinaryEncoding.Base64), Compression.Deflate)), let _t = ((type nullable text) meta [Serialized.Text = true]) in type table [userid = _t, productid = _t, value = _t, date = _t]),
        #"Grouped Rows" = Table.Group(Source, {"userid", "productid"}, { {"min", each List.Min([date]), type nullable text}}),
        #"Added Custom" = Table.AddColumn(#"Grouped Rows", "max", each Date.From( DateTime.LocalNow())-#duration(1,0,0,0)),
        #"Reordered Columns" = Table.ReorderColumns(#"Added Custom",{"userid", "productid", "min", "max"}),
        #"Changed Type with Locale" = Table.TransformColumnTypes(#"Reordered Columns", {{"min", type date}, {"max", type date}}, "en-US"),
        Custom1 = Table.AddColumn(#"Changed Type with Locale", "date", each {Number.From([min])..Number.From([max])}
    ),
        #"Expanded Custom" = Table.ExpandListColumn(Custom1, "date"),
        #"Changed Type" = Table.TransformColumnTypes(#"Expanded Custom",{{"date", type date}}),
        #"Removed Columns" = Table.RemoveColumns(#"Changed Type",{"min", "max"}),
        #"Merged Queries" = Table.NestedJoin(#"Removed Columns", {"userid", "productid", "date"}, Table, {"userid", "productid", "date"}, "Table", JoinKind.LeftOuter),
        #"Expanded Table" = Table.ExpandTableColumn(#"Merged Queries", "Table", {"value"}, {"Table.value"}),
        #"Sorted Rows" = Table.Sort(#"Expanded Table",{{"userid", Order.Ascending}, {"productid", Order.Ascending}, {"date", Order.Ascending}}),
        #"Filled Down" = Table.FillDown(#"Sorted Rows",{"Table.value"})
    in
        #"Filled Down"


    Best Regards,
    Community Support Team _ Yalan Wu
    If this post helps, then please consider Accept it as the solution to help the other members find it more quickly.

5 Replies

  • v-yalanwu-msft's avatar
    v-yalanwu-msft
    Community Support

    Hi, Anonymous ;

    You could duplicate a table as TableB, then grroup by the min date , and add yestoday date column.

    Then merge column from original table and TableB,

    Last sort and fill down.

    See the working here - Open a blank query - Home - Advanced Editor - Remove everything from there and paste the below code to test.

    let
        Source = Table.FromRows(Json.Document(Binary.Decompress(Binary.FromText("dc9JCsAgDAXQqxTXgeqPqelZxEV7/0N0ULB1CGQRePwkMRpnyBx3L7k28sz3qKvTFRYwiTI6K3KkwQ/R8UUs+iKgIrQIsnVJ+K9jsmIz2qc3lbzswNOznvIBHUP7IusYNVlOCpPC0gU=", BinaryEncoding.Base64), Compression.Deflate)), let _t = ((type nullable text) meta [Serialized.Text = true]) in type table [userid = _t, productid = _t, value = _t, date = _t]),
        #"Grouped Rows" = Table.Group(Source, {"userid", "productid"}, { {"min", each List.Min([date]), type nullable text}}),
        #"Added Custom" = Table.AddColumn(#"Grouped Rows", "max", each Date.From( DateTime.LocalNow())-#duration(1,0,0,0)),
        #"Reordered Columns" = Table.ReorderColumns(#"Added Custom",{"userid", "productid", "min", "max"}),
        #"Changed Type with Locale" = Table.TransformColumnTypes(#"Reordered Columns", {{"min", type date}, {"max", type date}}, "en-US"),
        Custom1 = Table.AddColumn(#"Changed Type with Locale", "date", each {Number.From([min])..Number.From([max])}
    ),
        #"Expanded Custom" = Table.ExpandListColumn(Custom1, "date"),
        #"Changed Type" = Table.TransformColumnTypes(#"Expanded Custom",{{"date", type date}}),
        #"Removed Columns" = Table.RemoveColumns(#"Changed Type",{"min", "max"}),
        #"Merged Queries" = Table.NestedJoin(#"Removed Columns", {"userid", "productid", "date"}, Table, {"userid", "productid", "date"}, "Table", JoinKind.LeftOuter),
        #"Expanded Table" = Table.ExpandTableColumn(#"Merged Queries", "Table", {"value"}, {"Table.value"}),
        #"Sorted Rows" = Table.Sort(#"Expanded Table",{{"userid", Order.Ascending}, {"productid", Order.Ascending}, {"date", Order.Ascending}}),
        #"Filled Down" = Table.FillDown(#"Sorted Rows",{"Table.value"})
    in
        #"Filled Down"


    Best Regards,
    Community Support Team _ Yalan Wu
    If this post helps, then please consider Accept it as the solution to help the other members find it more quickly.

  • Do a FULL OUTER JOIN to a table that lists all dates contiguously. Then expand that so that you have one day for every User/Product combinatin. (It's going to be a lot). Order by User ID and Product. Then do a FILL DOWN transform.

  • Anonymous's avatar
    Anonymous
    Not applicable

    ToddChitt Thank you,

     

    However I have tried this before but some days are still missing 

  • That seems sort of impossible. A FULL OUTER JOIN means take ALL ROWS from one table, and ALL ROWS from a second table, and if the dates match, put that data on one row, otherwise use whatever data you have from either row.

    So if you have a Calendar table with ALL DATES, how can it be missing dates.

    Can you share your Power Query M code, possible some sample data as well?