2011-08-14 5 views
5

73 대신 a1=72이 (끔찍한) C++ 코드 스 니펫으로 표시되는 이유는 무엇입니까? 이 예에서 다음 0.73 낮은 그것에 가까운 숫자로 반올림되도록캐스팅 변경 값이 이상하게

#include <iostream> 
#include <string> 

using namespace std; 

int main (int argc, char* argv[]) 
{ 
    double  a = 136.73; 
    unsigned int a1 = (100*(a-(int)a)); 

    cout << (a-(int)a)  << endl; // 0.73 
    cout << 100*(a-(int)a) << endl; // 73 
    cout << a1    << endl; // 72 ! 
} 

http://codepad.org/HhGwTFhw

+2

답변은 정밀도와 관련이 있어야합니다. 전에 여러 번 물었다. – iammilind

+1

IEEE754 부동 소수점 숫자의 이진 표현과 10 진수 근사에 관한 고유 한 제한에 대해 알고 계십니까? – fredoverflow

답변

8

, 당신은 그 (a - (int) a) 인쇄 0.7299999999999898를 볼 수 있습니다.

따라서, (당신이 int에 캐스팅 할 때 얻을)이 값의 truncation은 참으로 72입니다.

은 (codepad here 업데이트되었습니다.)

+0

+1에 대한 코드 패드. –

4

0.73 그것을 실행할 수 정확히 나타낼 수 없다. 100을 곱하면 72.[something]이되고 나중에 나중에 72으로 트림됩니다. 당신은 출력 정밀도를 높일 경우

more info

5

이 공통의 정밀도 문제입니다. 문자 적 136.73 실제로 수

136.729999999999989768184605054557323455810546875 

a-(int)a의 결과를 의미는 0.73 (즉, 표시되는 경우에도)이 아니라

0.729999999999989768184605054557323455810546875 

당신이 곱하면 그 100하면 get

72.9999999999989768184605054557323455810546875 

그리고 double에서 int로 변환하면 소수점 이하의 모든 것을 자르기 때문에 요 u는 72이됩니다.

+0

나인의 출현 후 소수점은 어디에서 오는가? – Klaus

+0

@Klaus : double이 내부적으로 저장되는 방식에 대해 읽어보십시오. – fredoverflow

4

다음 문서를 읽으면 분명해질 수 있습니다. What Every Computer Scientist Should Know About Floating-Point Arithmetic.

다른 사람들은 이미 (a - (int)a)의 결과가 정확히 0.73은 아니지만 조금 낮다는 것을 보여주었습니다. 기사는 이유를 설명합니다입니다. 그것은 정확하게 읽기 쉽지는 않지만 실제로 FP로 일하는 모든 사람들은 읽고 이해해야합니다. IMO.