← 질문 목록
#354깊이 0
0.1을 더했는데 왜 딱 안 떨어지는가?
언어 · 런타임기초
십진 0.1이 이진에서 끝나지 않는 소수라, 흔히 쓰는 실수 타입이 가장 가까운 값으로 반올림해 저장하기 때문이다.
- 0.1을 적는다
그다음은 이진으로는 끝없이 이어진다입니다. 그다음
이진으로는 끝없이 이어진다그다음은 정해진 자릿수 안에서 가장 가까운 값으로 반올림한다입니다. 그다음
정해진 자릿수 안에서 가장 가까운 값으로 반올림한다그다음은 계산할 때마다 그 차이가 더해지거나 상쇄되며 남는다입니다. 그다음
계산할 때마다 그 차이가 더해지거나 상쇄되며 남는다
십진에서 1을 3으로 나눈 값을 0.333…으로밖에 못 적는 것과 같은 일이다. 밑이 2인 자리로는 10분의 1을 유한하게 적을 수 없다.
그래서 배정밀도에서 0.1과 0.2를 더한 값은 0.3과 정확히 같지 않다. 계산을 거친 실수를 등호로 견주면 안 되는 이유가 이것이고, 견주려면 차이가 충분히 작은지를 본다.
표현할 수 있는 값의 간격은 값이 클수록 넓다. 그래서 규모가 크게 다른 두 수를 더하면 작은 쪽이 묻히기도 한다. 더하는 순서를 바꾸면 합이 달라질 수도 있다.
주의
돈은 이 타입으로 다루지 않는다. 십진 소수를 그대로 다루는 타입을 쓰거나, 가장 작은 단위의 정수로 바꿔 계산하고 보여줄 때만 나눈다.
이자나 환율처럼 나눗셈이 끼면 그것만으로 안 된다. 중간 계산을 몇 자리까지 들고 갈지와 어디서 반올림할지를 함께 정해야 한다.
표현의 한계와 계산 실수는 구분해야 한다. 정밀도를 올리면 오차가 작아질 뿐 성질은 그대로다.