Double.MaxValue以整数为负? [英] Double.MaxValue to integer is negative?

查看:151
本文介绍了Double.MaxValue以整数为负?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

为什么 Double.MaxValue 铸造为整型的结果为负值,该类型的最小值?

 双maxDouble = double.MaxValue; // 1.7976931348623157E + 308
长maxDoubleLong =(长)maxDouble; // -9223372036854775808
 

我会理解的一个编译器错误,如果它过大或发生OverflowException 在运行时,或者我会使用选中的转换可能不会抛出异常,但结果是不确定的和不正确(负)。

此外奇怪的是,该值是 long.MinValue

 布尔sameAsLongMin = maxDoubleLong == long.MinValue; // 真正
 

顺便说一句,同样的情况,如果我投它 INT

  INT maxDoubleInt =(INT)maxDouble; // -2147483648
布尔sameAsIntMin = maxDoubleInt == int.MinValue; // 真正
 

如果它试图将其转换为十进制我得到一个发生OverflowException 在运行时

 十进制maxDoubleDec =(十进制)maxDouble; //没了
 

更新:看来,迈克尔和巴里的回答一针见血的头部,如果我使用选中明确我得到一个发生OverflowException

 检查
{
    双maxDouble = double.MaxValue; // 1.7976931348623157E + 308
    长maxDoubleLong =(长)maxDouble; //没了
}
 

解决方案

C#语言规范(5.0版)说,在6.2.1显式数值转换下面的(强调):

  
      
  • 对于从float或double到整型的转换,处理取决于溢出检查上下文(§7.6.12),其中   发生转换:

         
        
    • 在选中的情况下,转换过程如下:

           
          
      • 如果操作数的值是NaN或无穷大,则引发System.OverflowException。
      •   
      • 否则,源操作数被四舍五入向零至最接近的整数值。如果此积分值的范围内   目标类型那么这个值是转换的结果。
      •   
      • 否则,则引发System.OverflowException。
      •   
    •   
    • 在unchecked上下文中,转换总是会成功,并进行如下:

           
          
      • 如果操作数的值是NaN或无穷大,转换的结果是目标类型的一个未经指定的值。
      •   
      • 否则,源操作数被四舍五入向零至最接近的整数值。如果此积分值的范围内   目标类型那么这个值是转换的结果。
      •   
      • ,否则,转换的结果是目标类型的一个未经指定的值。
      •   
    •   
  •   

而在7.6.12checked和unchecked运算符

  

有关非恒定的前pressions(即是在评估前pressions   运行时)不是由任何选中还是未选中运营封闭   或声明,默认溢出检查上下文是选中   除非外部因素(如编译器开关和执行   环境配置)要求检查评估。

有关从转换双十进制:如果源值为NaN,无穷大或过大,再present为小数,则将引发System.OverflowException。 检查 VS 选中不发挥作用(这些处理整体的操作只)。

Why does Double.MaxValue casted to an integral type results in a negative value, the smallest value of that type?

double maxDouble = double.MaxValue;       // 1.7976931348623157E+308
long maxDoubleLong = (long) maxDouble;    // -9223372036854775808

I'd understand a compiler error if it's too large or an OverflowException at runtime or if i'd use unchecked that the conversion might not throw an exception, but the result becomes undefined and incorrect(negative).

Also strange is that the value is long.MinValue:

bool sameAsLongMin = maxDoubleLong == long.MinValue; // true

By the way, the same happens if i cast it to int:

int maxDoubleInt = (int)maxDouble;                   // -2147483648
bool sameAsIntMin = maxDoubleInt == int.MinValue;    // true

If it try to cast it to decimal i get an OverflowException at runtime

decimal maxDoubleDec = (decimal)maxDouble;  // nope

Update: it seems that Michael's and Barre's answers hit the nail on the head, if i use checked explicitly i get an OverflowException:

checked
{
    double maxDouble = double.MaxValue;     // 1.7976931348623157E+308
    long maxDoubleLong = (long) maxDouble;  // nope
}

解决方案

The C# Language Specification (Version 5.0) says the following in 6.2.1 "Explicit numeric conversions" (emphasis added):

  • For a conversion from float or double to an integral type, the processing depends on the overflow checking context (§7.6.12) in which the conversion takes place:

    • In a checked context, the conversion proceeds as follows:

      • If the value of the operand is NaN or infinite, a System.OverflowException is thrown.
      • Otherwise, the source operand is rounded towards zero to the nearest integral value. If this integral value is within the range of the destination type then this value is the result of the conversion.
      • Otherwise, a System.OverflowException is thrown.
    • In an unchecked context, the conversion always succeeds, and proceeds as follows.

      • If the value of the operand is NaN or infinite, the result of the conversion is an unspecified value of the destination type.
      • Otherwise, the source operand is rounded towards zero to the nearest integral value. If this integral value is within the range of the destination type then this value is the result of the conversion.
      • Otherwise, the result of the conversion is an unspecified value of the destination type.

And in 7.6.12 "The checked and unchecked operators"

For non-constant expressions (expressions that are evaluated at run-time) that are not enclosed by any checked or unchecked operators or statements, the default overflow checking context is unchecked unless external factors (such as compiler switches and execution environment configuration) call for checked evaluation.

For conversions from double to decimal: "If the source value is NaN, infinity, or too large to represent as a decimal, a System.OverflowException is thrown". checked vs unchecked doesn't come into play (those deal with integral operations only).

这篇关于Double.MaxValue以整数为负?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆