perl不一致的负零结果

smi*_*ith 6 floating-point perl

我有以下代码:

my $m=0;
my $e =0 ;
my $g=0;

my $x=  sprintf( "%0.1f", (0.6*$m+ 0.7 * $e-1.5)*$g);

print $x; 
Run Code Online (Sandbox Code Playgroud)

当我运行脚本时,结果是-0.0而不是0.0有人可以解释为什么以及如何将其更改为0.0.

ike*_*ami 6

首先,这与Perl无关.这是你的处理器返回-0.0.你会在其他语言中看到同样的行为.


你问为什么,大概问为什么这是有用的.老实说,我不知道.一些科学家和工程师可能会利用它.

+0.0表示"零点或正面稍微大一些".

-0.0表示"零或者在负面上稍微大一点的东西".


你也问如何摆脱这个标志.

负零是假的,$x || 0技巧也是如此.


Kei*_*son 3

你遇到了一些非常奇怪的事情。我的第一个想法是,您看到了一些非常小的负数,sprintf四舍五入为 -0.0,但实际上表达式的结果是实际的负零。

这是一个表现出相同问题的更简单的程序:

#!/usr/bin/perl

use strict;
use warnings;

my $x = -1.0 * 0.0;
my $y = -1.5 * 0.0;
printf "x = %f\n", $x;
printf "y = %f\n", $y;
Run Code Online (Sandbox Code Playgroud)

和输出:

x = 0.000000
y = -0.000000
Run Code Online (Sandbox Code Playgroud)

我最好的猜测是,它-1.0 * 0.0是在编译时计算的,但-1.5 * 0.0在执行时计算的,并且计算产生不同的结果。 编辑:删除那个;用函数调用替换所有常量的程序的修改版本具有相同的行为。

我可以通过在调用之前添加这些行来避免负零显示printf

$x += 0.0;
$y += 0.0;
Run Code Online (Sandbox Code Playgroud)

但这很难看。

(顺便说一句,大约一个月前,我使用 Perl 5.15.2 的“前沿”版本得到了相同的结果。)

类似的 C 程序会打印-0.000000x 和 y。

编辑:进一步的实验表明,将负整数值乘以 0.0 会得到 0.0,但将负非整数值乘以 0.0 会得到 -0.0。我已经提交了一份Perl 错误报告