1

I have simple function of calculating the sum of numbers and strings in columns in a table. The sum works well and gives me results. The issue is that the sum has a lot of decimal places and I want to convert it to 2 decimal places, whenever I try   

return sum.toFixed(2);

I end up with an error.

 Type 'string' is not assignable to type 'number'.

Example of the sum from some columns

615.7142868041998, 0,10, 34.0476188659667, 14.761905193328857

What I have so far. The table columns contains both integers and strings, am using the reducer function to get only numbers

getSum(columnNumber) {
    let sum = 0;
    const columnNumberToPropertyMap = [
      "id",
      "teamNumber",
      "rural",
      "completed",
      "entirehouseholdabsent",
      "postponed",
      "refused",
      "vacant",
      "dwelling"     
    ];
    const property = columnNumberToPropertyMap[columnNumber];
    return this.rural.reduce((acc, curr) => {
      //const adder = Number(curr[property]) || 0;
      const adder = isNaN(Number(curr[property])) ? 0 : Number(curr[property]);
      sum = acc + adder
      return sum.toFixed(2);
    }, 0);
  }

How can I convert the sum to 2 decimal places. I have tried to pipe the result in the html | number : '1.2-2' it is not working also . thank you in advance

Arghya C
  • 9,805
  • 2
  • 47
  • 66
arriff
  • 399
  • 1
  • 10
  • 30
  • `sum.toFixed(2)` returns a string. You should add types to your functions to find such errors much faster: `getSum(columnNumber: number): number {` – Thomas Sablik Feb 22 '21 at 21:18
  • keep track of your datatypes. javascript doesn't care, but typescript does. keep track if you are using strings or numbers. – Rick Feb 22 '21 at 21:20

2 Answers2

3

If you want to do the .toFixed after all the numbers have been summed, stick it after the reduce:

return this.rural.reduce((acc, curr) => {
  //const adder = Number(curr[property]) || 0;
  const adder = isNaN(Number(curr[property])) ? 0 : Number(curr[property]);
  sum = acc + adder
  return sum;
}, 0).toFixed(2);
James
  • 20,957
  • 5
  • 26
  • 41
2

.toFixed() converts the number into a string, that's why you are getting the error. You can convert it back to number like

parseFloat(sum.toFixed(2))

You can also create a utility function like

const formatDecimalNumber = (
    num: number,
    decimalPlacesToKeep = 2,
): number => parseFloat(num.toFixed(decimalPlacesToKeep))

Update

As pointed out in the comment, this is not a perfect solution. It all comes from the complexities of floating point math (not only limited to JavaScript). There's very good discussion in this thread.

On the other hand, .toFixed() is more like an utility function that rounds off and/or adjusts a number for easy representation. See docs here.

Some alternatives to this is approach is discussed here.

Arghya C
  • 9,805
  • 2
  • 47
  • 66
  • 1
    You might want to add *why* [`.toFixed` returns a string...](https://stackoverflow.com/questions/588004/is-floating-point-math-broken) which will also be a problem with your idea of parsing it back to a float... – Jared Smith Feb 22 '21 at 21:32