숫자 변환이 값을 변경하는지 테스트하는 방법은 무엇입니까?

StackOverflow https://stackoverflow.com/questions/1601646

  •  05-07-2019
  •  | 
  •  

문제

표현 해야하는 데이터 유형 변환을 수행하고 있습니다. uint, long, ulong 그리고 decimal IEEE 754 이중 부동 소수점 값. IEEE 754 데이터 유형이 변환을 수행하기 전에 값을 포함 할 수 없는지 감지 할 수 있기를 원합니다.

Brute Force 솔루션은 캐스트 주위에 시도를하는 것입니다. OverflowException. 특정을 통해 읽습니다 CLR 문서 일부 변환은 예외없이 값을 조용히 변경 함을 의미합니다.

이 수표를 수행하는 바보 증거 방법이 있습니까? 구현 용이성보다 완전성을 찾고 있습니다. IEEE 754 사양을 면밀히 읽고 메이사와 지수를 신중하게 확인할 것 같은 느낌이 듭니다 ...

나는 그것을 추가해야한다 대부분 정수를 정확하게 표현하고 부동 소수점 정밀도의 손실은 이차적 인 관심사입니다 (그러나 여전히 고려할 가치가 있음).

편집하다: INT32는 IEE-754로 완전히 표현 될 수 있습니다. 또한 Decimal 데이터 유형은 질문의 일부입니다.

중요한 업데이트 : 이 질문을 언급하는 경우이 질문도 읽어야합니다. IEEE-754 Double (64 비트 부동 소수점) vs. Long (64 비트 정수) 재 방문

그것은 매우 큰 값이 IEEE-754로 정확하게 표현 될 수있는 대답의 결함에 주목합니다. 이것은 값이 원래의 목적을 위해 값이 올바르게 왕복 될 것이라는 것을 의미 할 수 있지만 (JavaScript로 왕복 할 것인가).

또한 CLRS 시스템에는 버그가있는 것으로 보입니다.이 값이 왕복을 올바르게 허용하지 않기 때문에 Double 유형.

도움이 되었습니까?

해결책

간단한 솔루션은 다음과 같습니다.x 인 경우 int):

if ((int)(double)x != x) { 
  // won't convert
} else {
  // will convert
}

그리고 오랫동안 등.

(double) x는 x를 int에서 더블로 변환합니다. 그런 다음 (int)가 다시 변환합니다. 따라서 (int) (double) x 변환은 int를 이중으로 형성 한 다음 뒤로 형성합니다. 본질적으로 코드는 이중으로의 변환이 가역적인지 확인하고 있습니다 (따라서 이중은 INT의 정확한 값을 저장할 수 있음).

다른 팁

이것은 주로 작동하는 수 범위에 따라 다릅니다. 당신이 15 자리 내에있는 한 더블), 당신은 정수에 대한 안전한쪽에 있어야합니다.

기본적으로 고려해야 할 것은 중요한 숫자의 수입니다. 따라서 숫자가 중요한 숫자 한계보다 작다면 정확한 상태로 유지됩니다. 더 커지면 정밀도를 잃을 것입니다 (정수 인 경우에도).

당신의 숫자가 <2^53 인 한, 당신은 보통 좋습니다.

IEEE 754 Double은 Mantissa에 대해 52 비트를 가지고 있으며 당신은/to에서/to로 변환합니다. 정수/긴 따라서 테스트하기가 매우 쉽습니다. 정수가 52 비트 미만을 소비하면 IEEE 754 더블에 문제없이 변환 할 수 있어야합니다.

나는 int가 32 비트이고 긴 길이는 64 비트라고 생각합니다 (Java의 경우 C#이지만 C#과 Lazy를 확인하기 위해서는 확실히 알고 있습니다). 따라서 int는 부호와 부호를 모두 문제없이 두 배로 맞출 수 있습니다.

Ulong의 경우, 단순히 52 번째 비트보다 높은 비트가 ((Aulong && 0xfff0000000000000) == 0 인 경우 간단합니다.

오랫동안, 당신은 고려 사항에 사인을 가져와야합니다. Long은 두 번째로 상정되지만 IEEE754는 (단지 음의 비트가 없음), 긍정적으로 길고 (*-1) 긍정적 인 것처럼 점검하는 것이 안전하다고 생각합니다. 따라서 길이가 음수이라면 먼저 -1로 시간을 보내십시오 (긍정적으로는 아무것도하지 않습니다). 그런 다음 Ulong처럼 확인하십시오.

도움이 되었기를 바랍니다.

라이센스 : CC-BY-SA ~와 함께 속성
제휴하지 않습니다 StackOverflow
scroll top