2013-02-13 4 views
4

고유 한 부동 소수점 오류로 인한 문제를 피하려면 부동 소수점 형식의 값을 신중하게 비교해야합니다. 값을 오류 임계 값과 비교하여이를 향상시킬 수 있습니다. 위의 솔루션은 다음과 같은 자원에서 파생 된 float와 double 값을 델타와 비교합니까?

static float CompareRelativeError(float x, float y) { 
    return Math.Abs(x - y)/Math.Max(Math.Abs(x), Math.Abs(y)); 
} 
static bool CompareAlmostEqual(float x, float y, float delta) { 
    return x == y || CompareRelativeError(x, y) < delta; 
} 

// apologies if this is a poor example 
if (CompareAlmostEqual(1f/10f, 0.1f)) { ... } 

을 : Is it safe when compare 2 float/double directly in Java?

내가 할 수 없었던 반면 예를 들어

는 다음과 같은 해결책은 간단 x == y 테스트보다 더 사용할 수있다 이것을 확인하기위한 문헌을 찾으십시오. 같은 질문이 x > y과 같은 비교를 위해 유효해야합니다. xy은 본질적으로 동일한 경우 예를 들어, 어떻게 하나 ...

static bool CompareGreater(float x, float y, float delta) { 
    return x > y && !CompareAlmostEqual(x, y, delta); 
} 

다른 것보다 더 클 수 있으며, 따라서 다음은 x >= y 유효 될 것이다 :

static bool CompareGreaterOrEqual(float x, float y) { 
    return x >= y; 
} 

올바른 내 가정인가 ?

+0

가능한 복제본 [Doub le.epsilon에 대한 평등,보다 큰,보다 작음, 작거나 같음, 크거나 같음] (http://stackoverflow.com/questions/2411392/double-epsilon-for-equality-greater-thanless -than-less-than-equal-to-gre) –

답변

4

동등성 검사는 델타 (또는 엡실론) 기술이 부동 소수점 값에 사용되는 이유입니다.

우리는 3을 2.999999 ...와 같게하고 싶습니다.

static bool CompareGreaterOrEqual(float x, float y) { 
    return x >= y; 
} 

그것은해야한다 :로 정의 할 때

그래서 CompareGreaterOrEqual 방법은 충분하지 않다

static bool CompareGreaterOrEqual(float x, float y, float delta) { 
    return x >= y || CompareAlmostEqual(x, y, delta); 
} 

참고 : 델타 비교를 돌봐 이후 첫 번째 테스트에서 x >= yx > y 수 등호 :

static bool CompareGreaterOrEqual(float x, float y, float delta) { 
    return x > y || CompareAlmostEqual(x, y, delta); 
} 
+0

도와 주셔서 대단히 감사합니다! 이것은 매우 잘 쓰여진 답변이며 왜 지금 'CompareAlmostEqual'이 필요한지 이해합니다. –

2

이 경우 교환 원 =CompareAlmostEqual을 통해 이루어 졌으므로 CompareGreaterOrEqual에서도 사용하는 것이 좋습니다. 그것은 매우 당신이 이러한 기능을 활용하는 것입니다 방법에 따라 달라집니다 동안

static bool CompareGreaterOrEqual(float x, float y, float delta) { 
    return x >= y || CompareAlmostEqual(x, y, delta); 
} 

또한, 나 또한 같은 값을 사용하기 위해 delta에게 수업 전반에 걸쳐 사용되는 상수 변수를 만들 것입니다 (대신 인수로 주위를 통과).

+0

+1. 나를 때려! ;) –

+1

@MitchWheat - 실제로 우리의 대답에 따라 시대를보고, 나는 당신이 승자라고 믿는다! –

관련 문제