abs和fabs有什么区别?

时间:2015-11-16 15:07:48

标签: c++ visual-studio-2013 cmath

我在python here上检查了absfabs之间的区别

据我所知,速度和传递的类型有一些区别,但我的问题与V.S上的原生c ++有关。

关于V.S. 我在Visual Studio 2013 (v120)上尝试了以下内容:

float f1= abs(-9.2); // f = 9.2
float f2= fabs(-9); // Compile error [*]

所以fabs(-9)它会给我一个编译器错误,但当我尝试执行以下操作时:

double i = -9;
float f2= fabs(i); // This will work fine

我从第一个代码中理解它不会编译,因为fabs(-9)需要一个double,而编译器无法将-9转换为-9.0,但在第二个代码中,编译器将转换{{1}在编译时到i=-9所以i=-9.0可以正常工作。

有更好的解释吗?

另一件事,为什么编译器不能接受fabs(i)并将int值自动转换为像c#中那样自动加倍?

fabs(-9)

3 个答案:

答案 0 :(得分:16)

在C ++中,std::abs对于有符号整数和浮点类型都会重载。 std::fabs仅处理浮点类型(前C ++ 11)。请注意,std::很重要,因遗留原因通常可用的C函数::abs只能处理int

的问题
float f2= fabs(-9);

不是没有从int-9的类型)到double的转换,而是编译器不知道要选择哪个转换(int - > floatdoublelong double)因为这三者中的每一个都有std::fabs。您的解决方法明确告诉编译器使用int - > double转换,因此歧义消失了。

C ++ 11通过添加double fabs( Integral arg );来解决此问题,abs将返回转换为double的任何整数类型的std::abs。显然,这种重载也可以在C ++ 98模式下使用libstdc ++和libc ++。

一般情况下,只需使用$(document).on("click", "a.anchor_class", function () { //click code here } ,它就会做正确的事情。 (Interesting pitfall指出@Shafik Yaghmour。无符号整数类型在C ++中做有趣的事情。)

答案 1 :(得分:2)

我的Visual C ++ 2008不知道从long double fabs(long double)float fabs(float)double fabs(double)中选择哪个。

在语句double i = -9;中,编译器会知道-9应转换为double,因为i的类型为double

abs()stdlib.h中声明,它将处理int值。

fabs()math.h中声明,它将处理double值。

答案 2 :(得分:1)

使用C ++ 11,单独使用abs()是非常危险的:

#include <iostream>
#include <cmath>

int main() {
    std::cout << abs(-2.5) << std::endl;
    return 0;
}

此程序输出2作为结果。 (See it live

始终使用std::abs()

#include <iostream>
#include <cmath>

int main() {
    std::cout << std::abs(-2.5) << std::endl;
    return 0;
}

此程序输出2.5

您可以使用using namespace std;避免意外结果,但我会反对它,因为它一般被视为不良做法,因为您必须搜索using指令以了解abs() 1}}表示int重载或double重载。