【发布时间】:2011-11-18 23:04:30
【问题描述】:
min 已被定义为宏时,如何调用 std::min?
【问题讨论】:
-
无情地
#undef min并使用标准设施。
min 已被定义为宏时,如何调用 std::min?
【问题讨论】:
#undef min 并使用标准设施。
(std::min)(x,y)
min 周围的括号防止宏扩展。这适用于所有函数宏。
【讨论】:
[n3290: 3.4.2] 中以调用这样的函数作为示例,很明显这会阻止宏扩展(C99 中的6.10.3/10;我相信 C90 中的措辞很接近。)
#define foo 5 宏的扩展,或者这种覆盖行为仅适用于函数?
在 Windows 上,您需要在包含任何 Windows 头文件之前定义 NOMINMAX,最好在预编译头文件的开头。
【讨论】:
在您的代码中使用#undef min,在#include <> 指令之后。
#include <...> // bad header that defines `min` macro
#ifdef min
#undef min
#endif
// rest f code.
附录:如果您之后需要保留min 宏的值,您可以在某些编译器上使用不可移植的解决方案暂时禁用其定义。例如,微软的 C++ 编译器有一个push_macro pragma,它似乎也是supported by GCC。
【讨论】:
min 作为一个宏,一开始就是一个 hack。最好避免它。如果您真的想要一个宏,请使用一个名为 MIN 的宏或其他不会发生冲突的宏。
min 函数和 min 宏的 C++ 语言结构。
您可以通过以下方式避免宏定义:
#undef#define NOMINMAX 等配置或类似配置,或避免包含有问题的标头)如果这些选项无法使用或您不想使用它们,您始终可以通过适当使用括号来避免调用类似函数的宏:
#include <algorithm>
#include <stdio.h>
#define min(x,y) (((x) < (y)) ? (x) : (y))
int main()
{
printf( "min is %d\n", (std::min)( 3, 5)); // note: the macro version of `min` is avoided
}
这是可移植的,并且从 C 的早期黑暗时代就开始工作。
【讨论】:
我发现了其他几种方法:
方法一:
using std::min;
min(a, b); // uses either the macro or the function (don't add side effects!)
方法二:
#ifndef BOOST_PREVENT_MACRO_SUBSTITUTION
#define BOOST_PREVENT_MACRO_SUBSTITUTION
#endif
...
std::min BOOST_PREVENT_MACRO_SUBSTITUTION(a, b)
【讨论】: