Tag:

C ++ 11嵌套宏调用?

它在C ++ std 16.3.4中说: 重新扫描生成的预处理标记序列[来自宏调用替换]以及源文件的所有后续预处理标记,以替换更多的宏名称。 如果在替换列表的扫描期间(不包括源文件的其余预处理标记)找到要替换的宏的名称,则不会替换它。 此外,如果任何嵌套替换遇到要替换的宏的名称,则不会替换它。 这些未替换的宏名称预处理令牌不再可用于进一步替换,即使它们稍后(重新)检查在其中否则将替换该宏名称预处理令牌的上下文中。 什么是嵌套宏替换? 具体考虑: #define f(x) 1 x #define g(x) 2 x g(f)(g)(3) 我原以为是: g(f)(g)(3) <– first replacement of g, ok 2 f(g)(3) <– nested replacement of f, ok 2 1 g(3) <– second nested replacement of g, don't replace, stop 然而gcc意外地继续进行第二次替换g,产生: 2 1 2 3 有任何想法吗? 更新: 经过大量研究后,让我通过一个更简单的例子来解决这个问题: […]

没有令牌字符串的cpp扩展宏

我正在阅读CPP宏扩展,并希望在未提供(可选)令牌字符串时理解扩展。 我发现gcc v4.8.4这样做: $ cat zz.c #define B (B) |B| $ gcc -E zz.c # 1 “zz.c” # 1 “” # 1 “” # 1 “zz.c” () | | 任何人都可以解释为什么扩展在一个实例中是零空间而在另一个实例中是一个?

如何使宏返回字符而不是字符串?

我有以下宏(跟进: 在C中编写宏时,如何找到参数的类型和printf说明符? ): #define mu_format_specifier(expression) _Generic((expression), unsigned long: “%lu”, int: “%i”) #define mu_assert_equal(actual, expected) do { \ if (actual != expected) { \ char *message = malloc(MAX_ERROR_MESSAGE_LENGTH); \ if (message == NULL) { printf(“malloc failed”); exit(1); } \ snprintf(message, MAX_ERROR_MESSAGE_LENGTH, \ “required: %s != %s, reality: %s == ” mu_format_specifier(actual), \ #actual, #expected, #actual, actual); […]

这个C宏是什么意思?

这是一个宏可以计算参数的数量。 和代码如: #define Y_TUPLE_SIZE_II(__args) Y_TUPLE_SIZE_I __args #define Y_TUPLE_SIZE_PREFIX__Y_TUPLE_SIZE_POSTFIX ,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,0 #define Y_TUPLE_SIZE_I(__p0,__p1,__p2,__p3,__p4,__p5,__p6,__p7,__p8,__p9,__p10,__p11,__p12,__p13,__p14,__p15,__p16,__p17,__p18,__p19,__p20,__p21,__p22,__p23,__p24,__p25,__p26,__p27,__p28,__p29,__p30,__p31,__n,…) __n #define MPL_ARGS_SIZE(…) Y_TUPLE_SIZE_II((Y_TUPLE_SIZE_PREFIX_ ## __VA_ARGS__ ## _Y_TUPLE_SIZE_POSTFIX,32,31,30,29,28,27,26,25,24,23,22,21,20,19,18,17,16,15,14,13,12,11,10,9,8,7,6,5,4,3,2,1,0)) // the running result ————————————— MPL_ARGS_SIZE(a,b,c,d,e,f,g)==7 MPL_ARGS_SIZE(a,b,c,d)==4 如何理解 #define Y_TUPLE_SIZE_PREFIX__Y_TUPLE_SIZE_POSTFIX ,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,0 和 Y_TUPLE_SIZE_PREFIX_ ## __VA_ARGS__ ## _Y_TUPLE_SIZE_POSTFIX ? 顺便说一下,我知道##(磅,磅)的用法和#define Y_TUPLE_SIZE_I的机制

混淆宏扩展

可能重复: 谁能解释这些未定义的行为(i = i ++ + ++ i,i = i ++等…) 以下宏可能给应用程序带来哪些问题? 我编写了一个带有宏扩展的示例应用程序,用于在我的iOS(Objective C代码)中实现它。 它是这样的: #define SQUARE(x) ( x * x ) main( ) { int i = 3, j, k ; j = SQUARE( i++ ) ; k = SQUARE( ++i ) ; printf ( “\nValue of i++ = %d\nValue of ++i = %d”, […]

C块变为表达式:({int a = 1; int b = 2; a + b;})等于3

在阅读http://en.wikipedia.org/wiki/C_preprocessor#Multiple_evaluation_of_side_effects时 ,我遇到了这个例子: \#define max(a,b) \ ({ typeof (a) _a = (a); \ typeof (b) _b = (b); \ _a > _b ? _a : _b; }) // WHY DOES THIS LINE WORK? 你可以像函数一样使用它,即max(1,2)是一个评估为2的表达式。 我的问题是, ({ statment-list last-expression; })构造如何计算last-expression的值? 具体来说,这个结构的解析树是什么样的? 我认为{ }总是指复合语句,而语句没有值。 我试着在C语法中挖掘,仍然无法解决这个问题。

为什么在c / c ++中需要两个括号来使用宏?

KdPrint((“Enter HelloWDMAddDevice\n”)); 这样做的原因是什么?

C中未命名的参数

在C中,与C ++不同,必须命名函数定义的所有参数。 我没有使用(void)a撤消“未使用的参数”错误,或者公开使用__attribute__((unused)) ,而是创建了以下宏: #define UNUSED2(var, uniq) UNUSED_ ## line ## var __attribute((unused)) // squash unused variable warnings, can it be done without var? #define UNUSED(var) UNUSED2(var, __func__) 像这样使用 void blah(char const *UNUSED(path)) {} 有什么方法我可以保证一个独特的“虚拟”变量名称(显然LINE和__func__不能削减它),或忽略命名未使用的变量? Update0 最终使用的代码可在此处获得 。 #ifdef __cplusplus // C++ allows you to omit parameter names if they’re unused # define OMIT_PARAM #else […]

有没有办法检查宏是否已定义,并且它同时等于某个值

我经常使用类似对象的预处理器宏作为C代码中的布尔标志来打开和关闭代码段。 例如 #define DEBUG_PRINT 1 然后像使用它一样 #if(DEBUG_PRINT == 1) printf(“%s”, “Testing”); #endif 但是,如果包含#define的头文件忘记包含在源代码中,则会出现问题。 由于未声明宏,因此预处理器将其视为等于0,并且#if语句永远不会运行。 当忘记包含头文件时,可能发生非预期的,不守规矩的行为。 理想情况下,我希望能够检查宏是否已定义,并在一行中检查它是否等于某个值。 如果未定义,则预处理器会抛出错误(或警告)。 我正在寻找以下内容: #if-def-and-true-else-throw-error(DEBUG_PRINT) … #endif 它就像#ifdef和#if的组合,如果它不存在,则使用#error 。 我已经探索了一些途径,但是,预处理器指令不能在#define块中使用,据我所知,如果在内部使用宏时没有定义宏,则没有预处理器选项来抛出错误/警告#if语句。

过度依赖宏

我觉得,每次我读C或C ++程序时,其中一半或更多只是宏。 我知道宏可以很酷,但它们很难跟踪,调试等。更不用说大多数编程语言甚至没有定义像宏这样的东西(尽管Perl6会有类似的东西)。 我个人总是找到一种方法来编写我的代码而不使用宏,无论是模板,多重inheritance等。我甚至觉得我不是一个优秀的程序员,因为所有的专业人员使用宏,我尽量避免使用它们如我所能。 问题是,如果没有宏,是否存在无法解决的问题? 宏最终是一个好/坏的做法? 我什么时候应该考虑使用宏?