【问题标题】:What Standard Calls are Actually Macros什么是标准调用实际上是宏
【发布时间】:2017-06-05 13:05:33
【问题描述】:

我向here 提出了一个关于assert 的问题,该问题在标准中作为宏而不是函数实现。

这给我带来了一个问题,因为assert 似乎是一个函数,它采用参数的方式:assert(true) 因此我尝试将它用作:std::assert(true),当然是一个宏没用。

我的问题是:标准库提供的其他宏是否会显示为带参数的函数?

【问题讨论】:

  • 您可以找到一份标准的副本here - 现在开始阅读 ;-)
  • offsetof 是一个典型的类似函数的宏。其他函数可以实现为宏或适当的函数(尽管对于 C 函数更是如此,因为所有 C++ 函数都必须位于 std 命名空间中)。
  • @riodoro1 你不需要某些东西成为宏就能以这种方式关闭它..
  • @JesperJuhl 是的,但您确实需要它是一个宏才能打印断言失败的表达式。
  • 您将不得不查看 C。[headers]/5 在 C 中定义为宏的名称应在 C++ 标准库中定义为宏,即使 C 授予作为功​​能实施的许可证。 [ 注意:在 C 中定义为宏的名称包括:assert、offsetof、setjmp、va_arg、va_end 和 va_start。 ——尾注]

标签: c++ parameters macros namespaces assert


【解决方案1】:

如果我们查看 [标题] 第 5 和第 6 段,我们有

在 C 中定义为宏的名称应在 C++ 标准库中定义为宏,即使 C 授予作为函数实现的许可。 [ 注意:在 C 中定义为宏的名称包括:assertoffsetofsetjmpva_argva_endva_start。 ——尾注]

在 C 中定义为函数的名称应在 C++ 标准库中定义为函数。

所以,如果它在 C 中定义为宏,那么它将是 C++ 中的宏。不过有几个例外。来自 [support.runtime] 第 7 和 8 段

标头<cstdalign>和标头<stdalign.h>不得定义名为alignas的宏。

标头<cstdbool>和标头<stdbool.h>不得定义名为booltruefalse的宏。

尽管 [headers]/7 也涵盖了这些异常

在 C++ 中作为关键字或运算符的标识符不应在 C++ 标准库头文件中定义为宏。

还有一个例外,即在 7.12.3 分类宏中定义的所有分类宏都被每个 [c.math]/10 的函数重载

分类/比较函数的行为与 C 宏的行为相同,相应名称在 7.12.3,分类宏和 7.12.14,C 标准中的比较宏中定义。每个函数都为三种浮点类型重载,如下:

int fpclassify(float x);
bool isfinite(float x);
bool isinf(float x);
bool isnan(float x);
bool isnormal(float x);
bool signbit(float x);
bool isgreater(float x, float y);
bool isgreaterequal(float x, float y);
bool isless(float x, float y);
bool islessequal(float x, float y);
bool islessgreater(float x, float y);
bool isunordered(float x, float y);
int fpclassify(double x);
bool isfinite(double x);
bool isinf(double x);
bool isnan(double x);
bool isnormal(double x);
bool signbit(double x);
bool isgreater(double x, double y);
bool isgreaterequal(double x, double y);
bool isless(double x, double y);
bool islessequal(double x, double y);
bool islessgreater(double x, double y);
bool isunordered(double x, double y);
int fpclassify(long double x);
bool isfinite(long double x);
bool isinf(long double x);
bool isnan(long double x);
bool isnormal(long double x);
bool signbit(long double x);
bool isgreater(long double x, long double y);
bool isgreaterequal(long double x, long double y);
bool isless(long double x, long double y);
bool islessequal(long double x, long double y);
bool islessgreater(long double x, long double y);
bool isunordered(long double x, long double y);

【讨论】:

  • 如果我记得,<math.h> 中有一些函数式宏实际上是<cmath> 中的函数,例如用于测试浮点值的isnanisinf。如果您要将 <math.h> 包含到 C++ 中,我希望一个好的实现能够为您提供函数(而不是宏),但谁知道呢?
  • @AdrianMcCarthy 哦,你说得对,在 C 中它们是宏:en.cppreference.com/w/c/numeric/math/isnan 但在 C++ 中它们是函数:en.cppreference.com/w/cpp/numeric/math/isnan 我想知道 Nathan Oliver 引用的要求在这里如何得到满足?跨度>
  • @AdrianMcCarthy 回答更新了为什么这些是函数。
  • @NathanOliver 我会再次支持你...但我不能...我明天会接受。
  • @JonathanMee 没问题,也没有义务。很高兴能提供帮助。
猜你喜欢
  • 1970-01-01
  • 2021-05-12
  • 2011-08-01
  • 2011-12-26
  • 1970-01-01
  • 1970-01-01
  • 2010-12-10
  • 2017-03-03
  • 2018-09-26
相关资源
最近更新 更多