什么时候数字不是魔法



我有一个这样的函数:

float_as_thousands_str_with_precision(value, precision)

如果我这样使用它:

float_as_thousands_str_with_precision(volts, 1)
float_as_thousands_str_with_precision(amps, 2)
float_as_thousands_str_with_precision(watts, 2)

那些 1/2 是幻数吗?

是的,它们是幻数。很明显,数字 1 和 2 指定了代码示例中的精度,但不是原因。为什么在这一点上,您需要安培和瓦特比伏特更精确?

此外,避免幻数可以让您集中代码更改,而不必在精度需要更改时搜索文本数字 2 时搜索代码。

我会提出这样的建议:

HIGH_PRECISION = 3;
MED_PRECISION = 2;
LOW_PRECISION = 1;

您的客户端代码如下所示:

float_as_thousands_str_with_precision(volts, LOW_PRECISION )
float_as_thousands_str_with_precision(amps, MED_PRECISION )
float_as_thousands_str_with_precision(watts, MED_PRECISION )

然后,如果将来您执行以下操作:

HIGH_PRECISION = 6;
MED_PRECISION = 4;
LOW_PRECISION = 2;

您要做的就是更改常量...

但是要尝试回答OP标题中的问题:

IMO 唯一可以真正使用且不被视为"魔术"的数字是 -1、0 和 1,当用于迭代、测试长度和大小以及许多数学运算时。使用常量实际上会混淆代码的一些示例:

for (int i=0; i<someCollection.Length; i++) {...}
if (someCollection.Length == 0) {...}
if (someCollection.Length < 1) {...}
int MyRidiculousSignReversalFunction(int i) {return i * -1;}

这些都是非常明显的例子。 例如,开始和第一个元素并递增 1,测试以查看集合是否为空并符号反转......荒谬,但可以作为一个例子。现在将所有 -1、0 和 1 值替换为 2:

for (int i=2; i<50; i+=2) {...}
if (someCollection.Length == 2) {...}
if (someCollection.Length < 2) {...}
int MyRidiculousDoublinglFunction(int i) {return i * 2;}

现在你开始问自己:为什么我要在第 3 个元素上开始迭代并检查其他元素?数字 50 有什么特别之处?具有两个元素的系列有什么特别之处?Doubler 的例子在这里实际上是有意义的,但你可以看到 2 和 50 的非 -1、0、1 值立即变得神奇,因为他们正在做的事情显然有一些特别的东西,我们不知道为什么。

不,他们不是。

在这种情况下,幻数将是一个具有无法解释含义的数字。在您的情况下,它指定了清晰可见的精度。

一个幻数是这样的:

int calculateFoo(int input)
{
  return 0x3557 * input;
}

您应该知道,短语"幻数"有多种含义。在这种情况下,它在源代码中指定了一个数字,这是周围环境无法解释的。在其他情况下,使用该短语,例如在文件头中,将其标识为某种类型的文件。

在以下情况下,文字数字不是幻数:

  • 它在一个地方使用一次,根据其上下文具有非常明确的目的
  • 它以如此普遍的频率和如此有限的上下文使用,以至于被广泛接受为非魔术(例如,人们经常接受的循环中的+1或-1不是魔术)。
  • 有些人认为零偏移的+1不是魔术。我没有。当我看到变量 + 1 时,我仍然想知道为什么,ZERO_OFFSET不会弄错。

至于以下示例场景:

float_as_thousands_str_with_precision(伏特,1)

而提议的

float_as_thousands_str_with_precision(伏特,HIGH_PRECISION)

如果具有 1 的

伏特的函数将重复用于同一目的,则 1 是神奇的。当然,这是"魔术",但不是因为含义不清楚,而是因为你只是多次出现。

保罗的回答集中在"无法解释的意义"部分,认为HIGH_PRECISION=3解释了目的。IMO,HIGH_PRECISION没有提供比 PRECISION_THREE 或 THREE 或 3 之类的更多的解释或价值。当然,3 高于 1,但它仍然不能解释为什么需要更高的精度,或者为什么精度存在差异。数字提供了与建议标签一样多的意图和清晰度。

为什么首先需要改变精度?作为一名工程人员,我可以假设有三个可能的原因:(a)真正的工程理由,即测量本身仅对X精度有效,因此显示器反映了这一点,或者(b)X精度只有足够的显示空间,或(c)观众不会关心任何高于X精度的东西,即使它可用。

这些是复杂的原因,很难在一个恒定的标签中捕捉到,并且可能更适合评论(解释为什么做某事)。

如果这些功能的使用在一个地方,而且只在一个地方,我不会认为数字是魔术。意图很明确。

供参考:

文字数字是魔术,当

  • "具有无法解释的含义或多次出现的唯一值可以(最好)替换为命名常量。 http://en.wikipedia.org/wiki/Magic_number_%28programming%29(第3个项目符号)

相关内容

  • 没有找到相关文章

最新更新