如何测试数字转换是否会改变值?

mck*_*mey 3 c# clr ieee-754

我执行某些数据类型转换,我需要代表uint,long,ulongdecimal为IEEE 754个浮点值.我希望能够在执行转换之前检测IEEE 754数据类型是否包含该值.

一个强力的解决方案是将一个试图捕捉包裹在一个演员周围,以寻找双倍OverflowException.阅读某些CLR文档意味着某些转换只是默默地更改值而没有任何异常.

有没有任何万无一失的方法来做这个检查?我正在寻求完整性而非易于实施.我有一种感觉,我将仔细阅读IEEE 754规范并仔细检查matissa和exponent ......

我应该补充一点,我关心的是准确地表示整数,浮点精度的损失是次要问题(但仍值得考虑).

编辑: Int32能够完全表达为IEE-754.此外,Decimal数据类型也是问题的一部分.

重要更新:如果您提到这个问题,您还应该阅读这个问题:IEEE-754双(64位浮点)与长(64位整数)重访

它注意到答案中的一个缺陷,其中一些非常大的值也能够由IEEE-754精确表示.虽然这可能意味着该值将正确地往返,为了我的原始目的(它将往返JavaScript)它不会.

此外,CLRs System.Double类型中似乎存在一个错误,因为它没有正确地允许这些值进行往返.

ato*_*ice 9

简单的解决方案可能是(如果x是一个int):

if ((int)(double)x != x) { 
  // won't convert
} else {
  // will convert
}
Run Code Online (Sandbox Code Playgroud)

等等等等

(double)x将x从int转换为double.(int)然后再将它转换回来.所以(int)(double)x将一个int转换为一个double然后再转换回来.本质上,代码检查转换为double是可逆的(因此double可以存储int的确切值).