Home > Enterprise >  Get number of element in macro without allocating global variable
Get number of element in macro without allocating global variable

Time:08-20

I have the following code:

#define SUB_LIST 1, 2, 3

uint8_t sub_array[] = {SUB_LIST};

#define SUB_LIST_SIZE (sizeof(sub_array) / sizeof(sub_array[0]))

uint8_t array[SUB_LIST_SIZE   X] = {0};

Here, sub_array[] exists only because I need it to get the number of elements in SUB_LIST. It is not used anywhere else, and thus it is quite a waste of memory.

It is possible to get the number of element in SUB_LIST without having to permanently allocate memory for sub_array[]?

CodePudding user response:

You can use a compound literal but it gets a bit messy if you want to avoid specifying the element type (here uint8_t) twice:

#define SUB_LIST_SIZE ( sizeof( (uint8_t[]){SUB_LIST} ) / sizeof(uint8_t) )

With this, a local, unnamed array will be created wherever the SUB_LIST_SIZE macro's code is encountered. That will be created with automatic storage duration (typically, on the stack), or may even optimized out by the compiler. 1

A short demo:

#include <stdio.h>
#include <stdint.h>

#define SUB_LIST 1, 2, 3
#define SUB_LIST_SIZE ( sizeof( (uint8_t[]){SUB_LIST} ) / sizeof(uint8_t) )

int main()
{
    #define X 42 // For example
    uint8_t array[SUB_LIST_SIZE   X] = { 0 };
    size_t arr_length = sizeof(array) / sizeof(array[0]);
    printf("Array length = %zu\n", arr_length);
    return 0;
}

1 This assumes that the macro is used at block scope, as it is in your declaration of array in main; if it is used at file scope, then a static (permanent) unnamed array will be created.

CodePudding user response:

Consider a macro such as this:

#define GET_SIZE(...) ( sizeof (uint8_t[]){ __VA_ARGS__} )

Usage:

GET_SIZE(SUB_LIST)

This creates a temporary compound literal array and places your list of item as initializer list to that array. The compound literal will almost certainly get optimized away in any scenario - in your case it will get replaced by the number 3 in the machine code.

  • Related