【问题标题】:Why does NaN exist?为什么存在 NaN?
【发布时间】:2019-05-12 05:16:07
【问题描述】:

我不是在问“为什么这个计算结果是 NaN”,我是在问“为什么 NaN 存在,而不是导致异常或错误?”

我一直在想这个问题,并偶尔与人们讨论它。

我得到的唯一答案是 “你不想尝试捕获每个除法运算,是吗?”“在某些情况下 NaN 是一个有效的结果”

话虽如此,我从未收到 NaN 是有效结果的具体示例。假设 NaN 永远不可能是一个有效的结果,我不明白它为什么存在。如果它出现,据我所知,你有一个错误。时期。

您希望程序崩溃并死机,以便您可以轻松找到出错的地方。这不是让程序乱跑,可能会写入损坏的数据,可能会发送损坏的数据,或者做各种讨厌的事情——在不可避免的崩溃之前。 (正如《务实的程序员》中所说——Crash, Don't Trash)

现在,我相信IEEE 754 的设计师比我聪明得多,这让我相信它的存在是有原因的。这是什么原因?

【问题讨论】:

  • 一方面,异常处理通常很慢,因此欢迎选择不使用它来处理一些简单的NaN 情况的代码。此外,C 中没有异常处理。
  • 原因可以在这里找到:stackoverflow.com/questions/2618059/in-java-what-does-nan-mean。它用于 IEEE 754 算术上未定义的值,例如 0/0 除法。
  • @πάνταῥεῖ 我不确定这怎么可能太宽泛了。这是一个关于 IEEE 754 设计决策的明确问题,值得商榷。五分钟的谷歌搜索对我来说只导致了一个半途而废的论点。 “1985 年没有例外”的理由并不令人信服;有信号。
  • “而不是导致异常”是关键,异常是有争议的。上个世纪的一场灾难,将期望启用异常的库与期望禁用它的库混在一起是一场噩梦。取得成功的唯一真正方法是禁用它们并让 NaN 完成它的工作。如果你有勇气,你可以推翻这个选择。

标签: floating-point nan ieee-754


【解决方案1】:

每当我写一些关于数学的东西时,我都害怕被真正的数学家用金属棒击倒,但是我们开始吧,面对我们的恐惧:

“为什么 NaN 存在,而不是导致异常或错误?”

因为它既不是异常也不是错误。这是一个完全有效的计算结果。您在数学中有几个用例,在这些用例中,您收到了“NaN”的等价物,即无法测量的东西。考虑计算两条平行线之间的交点。或the calculation of the mass of a photon

在这些情况下,您在代码中追求“生活的数学方面”(我可以想象这主要适用于科学软件),我们有以下情况:

  • 它们没有错误,变量具有它们需要的值,计算已经完成,这就是结果。可悲的是,它不是一个实数(可能是一个复数?可能是一个可以使用其他数学方法解决的不确定性?),但您仍然有计算的答案。
  • 他们也不例外,您的代码没有任何问题,这不是异常情况,这就是答案:“NaN”(您期望 42?)。无需在此处停止您的程序流程:告知用户该计算无解或未定,并让他满意(注意:我撒了一点谎,阅读最新段)。

您希望程序崩溃并死机,这样您就可以 很容易找到出错的地方。

您完全正确:如果 NaN 的概念在您的程序上下文中不是有效结果,您仍然可以将其作为异常或错误处理。想象一下计算必要的直径一个足球场的专栏并获得 NaN。呃……那肯定是个错误,我想建那个体育场,给我一个直径!你也完全错了:请不要告诉你会“很容易”找到出错的地方,因为你在 NaN 之后触发了异常。我认识一些调试气象模型的人想和你谈谈(这些方程式并不好玩)。

如今,您拥有许多库和实现,它们对什么是错误、什么是异常等做出固执的决定。IEEE 设计人员将决定权留给了您。语言编码员将这种能力传递给了你。明智地使用它。

如果你读到这里,让我告诉你,为了过于简单,我对你撒了一点谎。 IEEE 链接定义了两种 NaN,安静的和信令的。我一直在谈论安静的人,好人。 信号会导致您的软件出现异常(上溢、下溢等)。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2013-06-26
    • 2020-03-12
    • 2017-05-10
    • 2013-12-17
    • 2021-06-18
    • 2013-07-25
    • 2019-11-13
    相关资源
    最近更新 更多