4

so I currently have a struct that looks like this:

typedef struct example {
    bool arr[]; //i would like this to be an array of booleans,
                //but i don't know the size right now; this is
                //probably wrong
} example_t;

I also have a create function that looks like this:

example_t *newExample(int SIZE){
    example_t *example = malloc(sizeof(example_t));
    //initialize arr to a bool array of size SIZE, ideally all false!
    example->arr = ???
    return example;
}

And from this, I would be able to do something like:

 example_t *example = newExample(MAX);
 if ( example->arr[10] )
      ....

Is this possible in C, to create a variable sized array of booleans?

For Reference: I need someway to map integers to either a char* or bool, so I can call arr[num] and be able to get either a string/word or a true/false value. Both ways, I'm not sure how to declare, and then initialize with a variable size. Thanks in advance!

5 Answers 5

3

In C99 you can use flexible array members where the last member can be an array without a given dimension, but there must be at least 2 members in the struct.

You can use a pointer (here I am using int instead of bool for brevity):

#include <stdlib.h>
#include <stdio.h>

typedef struct example {
    int *arr;
} example_t;

static example_t *newExample(size_t SIZE)
{
    example_t *example = malloc(sizeof(example_t) + sizeof(int) * SIZE);

    example->arr = (int *)(example + 1);
    example->arr[5] = 5;
    return example;
}

int main(void)
{
    example_t *x = newExample(10);

    printf("%d\n", x->arr[5]);
    free(x);
    return 0;
}

But this doesn't make much sense, why not add a first member containing the number of elements?

#include <stdlib.h>
#include <stdio.h>

typedef struct example {
    size_t size;
    int arr[];
} example_t;

static example_t *newExample(size_t SIZE)
{
    example_t *example = malloc(sizeof(example_t) + sizeof(int) * SIZE);

    example->size = SIZE;
    example->arr[5] = 5;
    return example;
}

int main(void)
{
    example_t *x = newExample(10);

    printf("%d\n", x->arr[5]);
    free(x);
    return 0;
}

Using this method haves an advantage: you can pass the object to any function without passing an extra parameter for the size.

Sign up to request clarification or add additional context in comments.

1 Comment

I think OP asked for bool array initialization, not for int array. But the concept is same though.
2

You can do this by adding extra memory after example:

size_t boolsize = 10 * sizeof(bool);

struct example *ptr = malloc(sizeof *ptr + boolsize);

This way you call malloc only once and memory is layed out contiguously

Comments

1

The last member of a struct is allowed to be an array of unspecified size, known as "flexible array member", so your declaration is correct.* It's your responsibility to calculate the correct size for malloc, so in your case, do:

example_t* example = malloc(sizeof(example_t) + SIZE * sizeof(bool));

If you want it initialized to 0 (false in a typical bool type), either use calloc:

example_t* example = calloc(1, sizeof(example_t) + SIZE * sizeof(bool));

Or initialize after malloc using memset:

memset(example, 0, sizeof(example_t) + SIZE * sizeof(bool));

*) as long as there are other members in your struct preceeding the array. Otherwise the struct would be useless and you could just allocate the plain array:

bool *example = malloc(SIZE * sizeof(bool));

Comments

1

If you don't know the size of the array in advance you can simply make it a pointer and allocate it later.

typedef struct example {
    bool* arr;  // <-- Pointer
    int size;   // <-- Size of the array
} example_t;

Creating a new array follows the same steps.

example_t* newExample(int size) {
    int i;
    example_t* example = malloc(sizeof(example_t));
    example->arr = malloc(sizeof(bool) * size);
    example->size = size;
    for(i = 0; i < size; i++)
      example->arr[i] = false;
    return example;
}

Don't forget to free the memory of the bool arr and the struct itself after use!

Comments

0

Do these stuff:

Structure definition:

typedef struct example {
    bool *arr; 
} example_t;

Creation:

example_t *newExample(int SIZE){
    example_t *example = malloc(sizeof(example_t));
    example->arr = malloc(SIZE*sizeof(bool)) // allocate space for arr
    for(int i = 0;i < SIZE;i++)
        example->arr[i] = false; // initialize all of arr elements to false
    return example;
}

Optionally, you can also keep a variable in the struct to store the size of arr array (alongside the *arr), so that you can use that later when accessing the arr array.

You will have to manually use free() when the usage of the structure example is finished.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.