자바스크립트에서 소수점 숫자 연산을 하면, 생각지도 못한 오류가 발생한다. 아래처럼 콘솔창에 0.1 + 0.2를 입력하면, 0.3이 아니라 0.30000000000000004 가 나오는 걸 확인해볼 수 있다. 이렇게 소수점 계산 오류가 발생하는 이유와 어떤 방법으로 해결할 수 있는지에 대해 알아보려고 한다. Javascript를 다루다보면 한번쯤은 마주칠 수 있는 오류이기 때문에 나중에 또 당황하지 않도록 기억하고 넘어가자! (Javascript에서만 있는 오류는 아님)
원인
왜 이런 오류가 생기는걸까? 우리는 보통 계산을 할 때 '10진법'을 사용하지만, 우리와 다르게 컴퓨터는 계산을 할 때 0과 1만 사용하는 '2진법'을 사용한다. 그래서 10진법을 2진법으로 바꾸는 변환과정이 필요한데, 소수 중 일부는 이 과정에서 무한소수가 되어버린다. 하지만 컴퓨터 메모리에는 한계가 있어서 무한 소수를 다 담지 못하고 중간에 잘라서 유한 소수로 저장해버린다. 바로 이 과정에서 미세한 오차가 발생하는 것이다.
해결방법
그러면 이런 오류를 어떻게 해결해야 할까? 해결 방법은 다양한데, 대부분 결과값을 소수점 12번째 자리에서 반올림하는 방법을 사용한다.
1. toFixed() 메서드
toFixed()는 입력받은 숫자를, 매개변수만큼 자리수를 반올림해 String으로 반환해주는 함수이다. 다시말해 매개변수는 소수점 몇 번째 자리까지 나타낼 지를 나타낸다. 참고로 0부터 20까지 입력할 수 있다. 숫자예를 들어 아래처럼 매개변수를 2로 지정해주면, 소수점 둘째자리까지 반올림해서 나타낸다. default값은 0이기 때문에 toFixed()만 입력하면 소수를 정수로 만들 수 있다.
그리고 String으로 반환한다는 점을 주의하자! 'number '타입으로 사용하고 싶다면 Number() 메서드를 한번 더 사용해서 숫자로 변환해줘야 한다.
let result = (0.1 + 0.2).toFixed(2);
// '0.30'
Number(result);
// 0.3
2. Math.round() 메서드
Math 객체에 있는 Math.floor, Math.ceil, Math.trunc, Math.round 등의 메서드를 통해 소수 연산을 다룰 수도 있다. 이 중 Math.round()에 대해 살펴보자. Math.round()는 이름처럼 '반올림'을 해주는 함수이다. 매개변수로 들어온 값을 반올림한 후, 가장 가까운 정수 값을 반환한다. toFixed()의 매개변수를 0으로 지정해줬을 때처럼 정수값을 반환해준다는 점에 주의하자.
Math.round(20.49);
// 20
Math.round((0.1 + 0.2) * 10) / 10;
// 0.3
3. 기타 라이브러리
Javascript의 수학 라이브러리를 이용하면 좀 더 쉽게 계산을 할 수도 있다. Big.js, BigNumber.js, Decimal.js, mathjs 등의 라이브러리들이 있어서 찾아보고 취향에 따라(?) 사용하면 된다.
참고 자료
'Language > Javascript' 카테고리의 다른 글
ES6 주요 문법 정리 (1) Arrows, Classes, Enhanced Object Literals, Template Strings, Destructuring, Default Parameter, Rest, Spread (0) | 2021.01.07 |
---|---|
AJAX, 비동기, XMLHttpRequest (0) | 2021.01.06 |
Iteration (2) for in문, for of문의 차이점 (3) | 2021.01.03 |
Iteration (1) Iteration 프로토콜, Iterable / Iterater (0) | 2021.01.03 |
비동기 호출 (3) Timer API (0) | 2020.12.30 |
댓글