DanielSchreiberMendes
DanielSchreiberMendes

Reputation: 75

Is it possible to handle each element in a variadic macro at compile time in C?

Is it possible to archieve the following somehow? I am using gcc.

#define foo(argCount, ...)\
    FOR_EACH_IN_VA_ARGS_(argCount, element, __VA_ARGS__)\
    {\
        printf("%u", sizeof(element));\
    }

Thanks for your answers.

Upvotes: 5

Views: 282

Answers (2)

Petr Skocik
Petr Skocik

Reputation: 60067

This answer shows how you can do a foreach macro in the preprocessor: https://stackoverflow.com/a/51775003/1084774

Applied to your example, the argCount argument isn't needed and the stateful version isn't really possible because the preprocessor doesn't have mutable state outside of what's defined and what isn't, but you can have an apply-macro-to-each version:

#include "foreach.h" //generated header implementing BX_foreachc
#include <stdio.h>
#define prsz(X) printf("%zu\n", sizeof(X))
#define foo(...) BX_foreach(;,prsz,__VA_ARGS__)

int main(void)
{
    foo(char,short,int,long, long long);
    //expands to  printf("%zu\n", sizeof(char)) ; printf("%zu\n", sizeof(short)) ; printf("%zu\n", sizeof(int)) ; printf("%zu\n", sizeof(long)) ; printf("%zu\n", sizeof(long long));

 }

(relies on the foreach.h header generated by the script posted in the linked answer)

A much simpler way to do this is via a macro-argument-parametrized list macro:

#include <stdio.h>
#define PRSZ(X) printf("%zu\n", sizeof(X));
#define LIST(_) _(char) _(short) _(int) _(long) _(long long)
int main(void)
{
    LIST(PRSZ)
}

Either method is portable.

Upvotes: 3

vitaly.v.ch
vitaly.v.ch

Reputation: 2532

If argCount is a constant it could be imitated, otherwise, you will need support for some contemporary standard.

Upvotes: 0

Related Questions