Pau*_*sik 41 .net c# vb.net divide-by-zero .net-3.5
请考虑以下代码和评论:
Console.WriteLine(1 / 0); // will not compile, error: Division by constant zero
int i = 0;
Console.WriteLine(1 / i); // compiles, runs, throws: DivideByZeroException
double d = 0;
Console.WriteLine(1 / d); // compiles, runs, results in: Infinity
Run Code Online (Sandbox Code Playgroud)
我可以理解编译器在运行时主动检查除零常量和DivideByZeroException但是:
为什么在"除零"中使用双精度返回Infinity而不是抛出异常?这是设计还是错误?
只是为了踢,我也在VB.NET中做到了这一点,结果是"更一致":
dim d as double = 0.0
Console.WriteLine(1 / d) ' compiles, runs, results in: Infinity
dim i as Integer = 0
Console.WriteLine(1 / i) ' compiles, runs, results in: Infinity
Console.WriteLine(1 / 0) ' compiles, runs, results in: Infinity
Run Code Online (Sandbox Code Playgroud)
编辑:
基于kekekela的反馈,我运行了以下导致无穷大:
Console.WriteLine(1 / .0000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000001);
Run Code Online (Sandbox Code Playgroud)
这个测试似乎证实了这个想法,文字的双重0.0实际上是一个非常非常微小的部分,它将导致无限......
Dan*_*Tao 35
简而言之:double类型定义了无穷大的值,而int类型则没有.因此,在这种double情况下,计算结果是您可以在给定类型中实际表达的值,因为它已定义.在这种int情况下,无穷大没有价值,因此无法返回准确的结果.因此例外.
VB.NET做的事情略有不同; 整数除法使用/运算符自动生成浮点值.这是为了允许开发人员编写例如表达式1 / 2,并将其评估0.5,有些人会认为这是直观的.如果要查看与C#一致的行为,请尝试以下操作:
Console.WriteLine(1 \ 0)
Run Code Online (Sandbox Code Playgroud)
注意使用上面的整数除法运算符(\,不是/).我相信你会得到一个异常(或编译错误 - 不确定是哪个).
同样,试试这个:
Dim x As Object = 1 / 0
Console.WriteLine(x.GetType())
Run Code Online (Sandbox Code Playgroud)
上面的代码将输出System.Double.
至于关于不精确的观点,这是另一种看待它的方式.并不是该double类型没有正好为零的值(它确实如此); 相反,该double类型并不意味着首先在数学上提供精确的结果.(某些值可以准确表示,是的.但是计算没有给出准确性的承诺.)毕竟,数学表达式的1 / 0值没有定义(最后我检查过).但1 / x随着x逼近零,接近无穷大.因此,从这个角度来看,如果我们无法n / m 准确地表示大多数分数,那么将该x / 0案例视为近似并给出它所接近的值 - 至少定义无穷大是有意义的.
double是一个浮点数而不是一个精确的值,所以你真正从编译器的角度划分的是接近于零但不完全为零的东西.