C语言中的MIN和MAX定义在哪里?
实现这些最好的方法是什么,尽可能的泛型和类型安全?(主流编译器的编译器扩展/内置优先。)
C语言中的MIN和MAX定义在哪里?
实现这些最好的方法是什么,尽可能的泛型和类型安全?(主流编译器的编译器扩展/内置优先。)
当前回答
这是一个较晚的答案,由于最近的发展。由于OP接受了依赖于不可移植的GCC(和clang)扩展类型的答案-或“干净”ISO C的__typeof__ -在GCC -4.9有一个更好的解决方案。
#define max(x,y) ( \
{ __auto_type __x = (x); __auto_type __y = (y); \
__x > __y ? __x : __y; })
这个扩展的明显好处是每个宏参数只展开一次,不像__typeof__解决方案。
__auto_type是c++ 11的auto. type的有限形式。它不能(或不应该?)在c++代码中使用,尽管在使用c++ 11时没有很好的理由不使用auto的高级类型推断功能。
也就是说,我假设当宏包含在extern“C”{…}范围;例如,来自C头文件。AFAIK,这个扩展没有找到它的方式信息叮当
其他回答
两个整数a和b的最大值是(int)(0.5((a+b)+abs(a-b)))。这也可以用于(double)和fabs(a-b)用于double(类似于float)
C语言中的MIN和MAX定义在哪里?
他们不是。
实现这些的最好方法是什么,尽可能的泛型和类型安全(主流编译器的编译器扩展/内置首选)。
作为功能。我不会使用像#define MIN(X, Y) (((X) < (Y))这样的宏?(X):(Y)),特别是如果您计划部署您的代码。要么写你自己的,使用标准的fmax或fmin,或者在GCC语句表达式中使用GCC的typeof(你也会得到类型安全奖励)修复宏:
#define max(a,b) \
({ __typeof__ (a) _a = (a); \
__typeof__ (b) _b = (b); \
_a > _b ? _a : _b; })
每个人都说“哦,我知道双重求值,这没问题”,几个月后,你会连续几个小时调试最愚蠢的问题。
注意使用__typeof__而不是typeof:
如果你正在写一个头文件 必须工作时,包括在ISO C 程序,写__typeof__而不是 typeof。
我不认为它们是标准化宏。浮点数已经有了标准化的函数,fmax和fmin (fmaxf用于浮点数,fmaxl用于长双精度浮点数)。
您可以将它们作为宏实现,只要您了解副作用/双重评估的问题。
#define MAX(a,b) ((a) > (b) ? a : b)
#define MIN(a,b) ((a) < (b) ? a : b)
在大多数情况下,你可以把它留给编译器来决定你要做什么,并尽可能优化它。虽然这在像MAX(i++, j++)这样使用时会产生问题,但我怀疑是否有必要一次性检查增量值的最大值。先递增,然后检查。
它也在GNU libc (Linux)和FreeBSD版本的sys/param.h中提供,并具有dreamlax提供的定义。
在Debian上:
$ uname -sr
Linux 2.6.11
$ cat /etc/debian_version
5.0.2
$ egrep 'MIN\(|MAX\(' /usr/include/sys/param.h
#define MIN(a,b) (((a)<(b))?(a):(b))
#define MAX(a,b) (((a)>(b))?(a):(b))
$ head -n 2 /usr/include/sys/param.h | grep GNU
This file is part of the GNU C Library.
在FreeBSD上:
$ uname -sr
FreeBSD 5.5-STABLE
$ egrep 'MIN\(|MAX\(' /usr/include/sys/param.h
#define MIN(a,b) (((a)<(b))?(a):(b))
#define MAX(a,b) (((a)>(b))?(a):(b))
源存储库在这里:
GNU C库 FreeBSD
值得指出的是,如果你用三元运算来定义最小值和最大值,比如
#define MIN(a,b) (((a)<(b))?(a):(b))
#define MAX(a,b) (((a)>(b))?(a):(b))
然后,为了在fmin(-0.0,0.0)和fmax(-0.0,0.0)的特殊情况下获得相同的结果,您需要交换参数
fmax(a,b) = MAX(a,b)
fmin(a,b) = MIN(b,a)