Home > OS >  Correct way to work with multiple repeating loops for sum of values
Correct way to work with multiple repeating loops for sum of values

Time:12-09

I'm working on a function that aims to return a non-repeating list of years for all transactions.

So far it worked fine, but I also need to add up all the values of the transactions for each year that it returned in the first loop.

I tried different ways and without success.

public async getListYear(): Promise<any>{
    try{
        return await client
        .scan({
            TableName: 'dbPayments'
        })
        .promise()
        .then((response) => {

            let result = response.Items.filter((e, i) => {
                return response.Items.findIndex((x) => {
                    return x.date_created.substring(0,4) == e.date_created.substring(0,4)
                }) == i;
            });

            let years = [];
            let sum = [];

            for(let i = 0; i < result.length; i  ){
                const yearTransaction = new Date(response.Items[i]['date_created']).getFullYear();
                years.push(yearTransaction)
            }

            // Here is the problem, I tried as follows:
            for(let i = 0; i < response.Items.length; i  ){

                if(response.Items[i]['status_pgm'] == 'approved'){

                    for(let i = 0; i < years.length; i  ){

                        let year = new Date(response.Items[i]['date_created']).getFullYear();
                        let value = 0;
                        
                        if(year == years[i]){
                            value  = response.Items[i]['transaction_amount']
                        }

                        let data = {
                            years[i]: value
                        }
                        
                        sum.push(data)
                    }

                }

            }

            return {
                status: 200,
                list: years,
                totalSum: sum
            }

        })
        .catch((error: AxiosError) => {
            throw error;
        })
    }catch (e) {
        console.log(e);
        return {status: 500, msg: "error"}
    }
}

Table dbPayments:

id   | date_created                   | transaction_amount  | status_pgm
1      2022-10-29T20:54:40.294-04:00    45                    approved
2      2022-09-29T20:54:40.294-04:00    30                    approved
3      2022-08-29T20:54:40.294-04:00    25                    approved
4      2021-10-29T20:54:40.294-04:00    15                    approved
5      2021-09-29T20:54:40.294-04:00    10                    approved

I need to return the sum of values for each year, what is the best way to do this? In the code I put an example of how I tried to do it.

CodePudding user response:

First. I think this is the kind of operation should be done on the DB not in client.

But i notice some errors.

 for(let i = 0; i < response.Items.length; i  ){

            if(response.Items[i]['status_pgm'] == 'approved'){

                for(let i = 0; i < years.length; i  ){

Inner and outer loop both use i so this mught clash and mess up the looping.

  let year = new Date(response.Items[i]['date_created']).getFullYear();

I think this should be on outer loop not inner loop.

let value = 0;
                    
                    if(year == years[i]){
                        value  = response.Items[i]['transaction_amount']
                    }

                    let data = {
                        years[i]: value
                    }

value is set to 0 each time this piece of code is reaches, so no accumulation is actually made.

My reccomendation. Make a Map<number, number>, where key is year and value is the accumulated sum. Then you just could

for(let i = 0; i < response.Items.length; i  ){

            if(response.Items[i]['status_pgm'] == 'approved'){
               let year = new Date(response.Items[i]['date_created']).getFullYear();
               let value = response.Items[i]['transaction_amount'];
                 map.set(year, map.get(year)   value || value)
            }
}

And if you need it as a array of sums like in the example, you could then create the array by iterating over years array, and then pushing the corresbonding years sum into a sums array.

for(let i = 0; i < years.length; i  ){
    let year = years[i];
    let obj= {};
    obj[year] = map.get(year);
    sums.push(obj);
}
  • Related