1
\$\begingroup\$

I have class:

export class DayValue {
  date: string;
  status: string;
}

and statusToPointsMap:

  public static map: Map<string, number> = new Map([
    ['COMPLETED', 100],
    ['FAILED', -100],
    ['SKIPPED', 0],
  ]);

I want to create function which calculates avg result per given period of time, ie:

[
  [
    "2020-05-02",
    "COMPLETED"
  ],
  [
    "2020-05-01",
    "FAILED"
  ],
  [
    "2020-04-30",
    "FAILED"
  ],
  [
    "2020-04-29",
    "SKIPPED"
  ],
  [
    "2020-03-13",
    "SKIPPED"
  ]
]

to (groupped by month)

[ ["05-2020",0],
  [ "04-2020",-40],
  ["03-2020",0]

]

or(groupped by year):

["2020",-16]

I created a function which works as I wanted, but I'm wonder if there is any way to to it smarter?

  private calculateAvgPerPeriod(values: DayValue[], period: string): any[] {
    const resultArray = [];
    from(values).pipe(
      groupBy(dayValue => this.datePipe.transform(dayValue.date, period)),
      mergeMap(group => group.pipe(toArray())),
      map(array => [
          this.datePipe.transform(array[0].date, period),
          array
            .map(day => this.statusToPointsMap.get(day.status))
            .reduce((prev, curr) => prev + curr, 0) / array.length
        ]
      ))
      .subscribe(entry => {
        resultArray.push(entry);
      });
    return resultArray;
  }
\$\endgroup\$

1 Answer 1

3
\$\begingroup\$

You're using RxJS, but your inputs and outputs are plain arrays. It'd be simpler to either consume and return streams or replace RxJS with Lodash/Ramda/Underscore/native array methods/some iteration-based library.

(If you want to get really fancy or need to use the function in different contexts, you could write a transducer.)

You're using a class, a method and a static property, but it would be sufficient to have a type, a function and a module-local constant. And passing datePipe (or just a Date) and status => getPointsFromStatusToPointsMap(status) function as arguments would make the dependencies more explicit. But these are more like code style preferences.

Lastly, you're returning any, but you should always return unknown instead unless you really have to lie to the type system for some reason. And returning [string, number] or [Date, number] would be more convenient for the consumer.

\$\endgroup\$

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.