Business
Jobs
  • About Us
  • Solutions
    • Job Postings
      Post your job and receive qualified candidates in 48h.
    • Candidate Assessments
      500+ technical and psychological tests, plus anti-fraud.
    • Headhunting
      Tailor-made executive search from start to finish.
    • Payroll + EOR
      Payroll dispersal and EOR across 15+ LATAM countries.
  • Pricing
  • Jobs

0

230
Views
Using C defines to simplify constant definitions?

I have the following defines:

#define M(x) ( ((uint64_t) 1) << (x) )
#define Mx  M(0)
#define My  M(1)
#define Mz  M(2)

Quite often I need to rearrange the order of Mx, My, Mz, for example:

#define My  M(0)
#define Mz  M(1)
#define Mx  M(2)

How would I make this more generic in a sense of not having to correct M(0/1/2) every time, but just shuffle the lines?

#define POS ... 

#define My  M(POS)
#define Mz  M(POS)
#define Mx  M(POS)
over 4 years ago · Santiago Trujillo
2 answers
Answer question

0

You could use an extra macro in between that will select an appropriate argument from the permutation. The permutation would be a macro itself that can be undefined and redefined.

#define NTH0(a0,a1,a2) a0
#define NTH1(a0,a1,a2) a1
#define NTH2(a0,a1,a2) a2
#define NTH(n, perm) NTH ## n (perm)

#define Mx  M(NTH(0, PERM))
#define My  M(NTH(1, PERM))
#define Mz  M(NTH(2, PERM))

#define PERM 1,2,3

Mx
My
Mz

#undef PERM
#define PERM 3,2,1

Mx
My
Mz

When compiled with gcc -E it expands to:

M(1)
M(2)
M(3)




M(3)
M(2)
M(1)
over 4 years ago · Santiago Trujillo Report

0

The best solution might be to solve this with version control or #ifdef switches rather than function-like macros. Or perhaps generate the C source through a script.

Otherwise, the standard pre-processor way to list stuff while avoiding code repetition is "X macros", where you only need to change the values in a single place (called M_LIST in this example):

#include <stdio.h>
#include <inttypes.h>

#define M_LIST(X) \
  X(x,0)          \
  X(y,1)          \
  X(z,2)          \

#define M_enum(symbol,val) M##symbol##_bit = val,
enum { M_LIST(M_enum) };

#define M(symbol) ( 1ull << (M##symbol##_bit) )

int main (void)
{
  printf("%.16"PRIx64"\n", M(x));
  printf("%.16"PRIx64"\n", M(y));
  printf("%.16"PRIx64"\n", M(z));
}

Here a temporary enum is created, which will expand to: enum { Mx_bit = 0, My_bit = 1, Mz_bit = 2, }. These constants aren't used directly by your program, but only through the macro M.

over 4 years ago · Santiago Trujillo Report
Answer question
Find remote jobs

Discover the new way to find a job!

Top jobs
Top job categories
Business
Post vacancy Pricing Sales
Legal
Terms and conditions Privacy policy
© 2026 PeakU Inc. All Rights Reserved.
Andres GPT
Show me some job opportunities
There's an error!