본문 바로가기
C#

[C#] 부동 소수점 오차(플로팅 연산 오류)

by 코모's 2023. 12. 12.
반응형

- 발생원인

모든 십진수들이 floatin point number형태로 저장될 수 없기 때문이다.
'정수 + 소수'방식이 아니라 '지수 * 가수'방식으로 숫자를 2진법으로 변환한뒤 정수부분이 1의 자리+소수점으로 남을때까지 2로 나누고 나눈만큼 지수로 곱해주어 계산한다.
우리가 소숫점을 찍고 디버깅을 했을 때, 0.3, 12.4 등 정확하게 나오는 이유는 c#에서 ToString을 할때 round off error무시한 반올림 숫자가 반환되기 때문이다. 

- 해결방법
1. float의 int 캐스팅은 되도록 피하도록 하자.
2. double로 소수점의 정밀도를 높이거나 Epsilon을 사용하도록 하자
3. 비교 연산을 할 때는 등호를 사용하지 말것
4. 곱하기를 하여 (최대한)정수로 만들고 후에 다시 나누기를 하여 float로 만들자

- Epsilon란?
부동소수점 연산에서 반올림 오차와 같은 작은 부동소수점 값들을 처리하는 데 사용되는 매우 작은 값.

float a = 2f;
float b = 2f;

float epsilon = 1E-6;

if (Math.Abs(a - b) < epsilon)
{
    Console.WriteLine("a and b are approximately equal.");
}




반응형