我在C语言中的宏有什么问题?

我在C语言中的宏有什么问题?,c,C,哦!!我知道你的问题是什么: left operand of comma has no operator in #define MID(a,b,c) The expression cannot be used as a function in #define MIN 应该是 #define MIN (a,b,c) (MINIMUM(MINIMUM(a,b),c)) 预处理器对空格敏感;MIN标记与其参数列表(a,b,c)之间不能有任何空格。请删除MIN之后的空格,它应该是: #define

哦!!我知道你的问题是什么:

left operand of comma has no operator in #define MID(a,b,c)
The expression cannot be used as a function in #define MIN
应该是

#define MIN (a,b,c) (MINIMUM(MINIMUM(a,b),c))

预处理器对空格敏感;
MIN
标记与其参数列表
(a,b,c)
之间不能有任何空格。请删除MIN之后的空格,它应该是:

#define MIN(a,b,c) (MINIMUM(MINIMUM(a,b),c))

它是有效的。

以您目前的方式使用宏时,存在几个问题。宏背后的想法是使编码更简单,但是因为没有类型检查,所以充满了危险:

问题-无类型检查: 如果你看的是
mid(a,b,c)
,那就更糟了

结论 请不要这样写代码

如果您坚持使用没有非标准
typeof
运算符的编译器,那么最好使用stdtypes.h和stdint.h并声明函数:

#include <stdio.h>

#define max(a,b)  ((a) > (b) ? (a):(b))

int main() {
     int a = 1, b = 2;
     printf("max(%d, %d) = %d\n", a, b, max(a, b));
     printf("max(%d, %d) = %d\n", a, b, max(a++, b++));
     printf("max(%d, %d) = %d\n", a, b, max(a, b));
     return 0;
 }
如果编译器具有
typeof
type运算符,则可以使用:

int main() {
     printf("%u", min_uint32_t(3, -5));
     printf("%d", min_int64_t(-1, -5));
} 
GCC特定 如果您使用的是足够新的gcc版本,那么如果您使用的是gcc,那么您应该使用
\uu auto\u type
而不是
typeof

#define max(a,b) \
  ({ typeof (a) _a = (a); \
      typeof (b) _b = (b); \
    _a > _b ? _a : _b; })
根据gcc类型手册页]:

使用
\u auto\u type
代替
typeof
有两个优点:

  • 宏的每个参数在展开时仅显示一次 宏。这将防止宏扩展的大小增长 当对此类宏的调用嵌套在参数中时,以指数形式进行 这样的宏

  • 如果宏的参数已可变地修改 类型,使用_uauto_utype时仅计算一次,如果 使用typeof

  • C++
    这是另一个完整的讨论:-)

    为什么不使用编译器查看预处理器输出?例如gcc和clang中的标志
    -E
    ,我在宏中添加了括号,它扩展为
    float t=(((a)>(b)?(a):(b))>(c)?(((a)>(b):(b)):(c))+(a,b,c)(a)我赞同预处理器的建议,但通常也会在括号中看到宏参数,以确保正确的计算顺序:
    #定义最大值(A,B)((A)>(B)?(A):(B))
    始终将宏参数括在括号中,以避免它们之间的错误关联。同时将结果括起来(例如,您的
    MID
    宏)例如,使用
    #定义添加(x,y)x+y((x)+(y))
    而不是
    #定义添加(x,y)((x)+(y))
    对不起,请您详细说明一下,我只是从宏开始。此外,请为参数a和b添加保护解释:使用
    最小值(a,b,c)
    扩展到实际值
    (a,b,c)(最小值(a,b,c))(a,b,c)
    由于
    a
    ,…存在于您的代码中,因此错误很奇怪hell@Jean-弗朗索瓦·法布:在什么情况下你可以调用
    MIN(a,b,c)
    并将参数传递给其他宏,使其被误解?在
    最小值
    最大值
    宏中,参数都应该用括号括起来,以防止误解,但我不确定当宏参数作为参数传递给其他宏时,是否有办法让事情被误解(假设其他宏本身是安全的)。我的意思是:用错误的定义使用
    MIN(a,b,c)
    只会将
    MIN
    定义为
    (a,b,c)…但是无论
    最小值
    最大值
    宏需要什么保护
    
    #include <stdio.h>
    
    #define max(a,b)  ((a) > (b) ? (a):(b))
    
    int main() {
         int a = 1, b = 2;
         printf("max(%d, %d) = %d\n", a, b, max(a, b));
         printf("max(%d, %d) = %d\n", a, b, max(a++, b++));
         printf("max(%d, %d) = %d\n", a, b, max(a, b));
         return 0;
     }
    
    #define __declare_min(__type) __inline__ static __type min_ ## __type(__type a, __type b) { return a < b ? a : b;  } 
    
    __declare_min(uint32_t)
    __declare_min(int64_t)
    
    int main() {
         printf("%u", min_uint32_t(3, -5));
         printf("%d", min_int64_t(-1, -5));
    } 
    
    #define max(a,b) \
      ({ typeof (a) _a = (a); \
          typeof (b) _b = (b); \
        _a > _b ? _a : _b; })
    
    #define max(a,b) \
      ({ __auto_type _a = (a); \
          __auto_type _b = (b); \
        _a > _b ? _a : _b; })