cheater
cheater

Reputation: 93

different ways to allocate memory for a data structure on c programming language

On C programming language, I have encountered several ways to allocate memory for a data structure:

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

typedef struct Element
{
    int number;
    struct Element *next;
}Element;

int main(int argc, char *argv[])
{
    /* Method NO.1 */
    Element *ptr1 = malloc(sizeof(*ptr1));
    /* Method NO.2 */
    Element *ptr2 = malloc(sizeof(Element));
    /* Method NO.3 */
    Element *ptr3 = (Element*) malloc (sizeof(Element));

    return EXIT_SUCCESS;
}

There are no compilation errors.
But I got confused, so what is the difference beteween them, and which one should be preferred?

Upvotes: 1

Views: 118

Answers (3)

dbush
dbush

Reputation: 225807

The first method is the preferred way of doing this. It allocates space for sizeof(*ptr1) bytes, where *ptr1 is the structure in question. If for some reason the type of this variable is modified, the above allocation will still work.

The second method is correct because it allocates space for sizeof(Element) bytes, which is the size of the structure. It is not preferred however, because if the type of ptr1 is changed for some reason but the expression above is not, you won't be allocating the proper amount of space.

The third method is not correct because you should not cast the return value of malloc.

Upvotes: 1

Bathsheba
Bathsheba

Reputation: 234875

  1. The best way by, in my opinion, a country mile. Remember that sizeof *ptr1 is compile-time evaluable so there's no chance of a run-time crash due to dereferencing an uninitialised pointer.

  2. Not my favourite way - despite it arguably being the most readable - since you might change the type of *ptr2 and forget to adjust sizeof Element. And those kind of bugs are a nightmare to track down.

  3. Is horrible: the cast is unnecessary in C and is even occasionally harmful. See Do I cast the result of malloc?.

Upvotes: 2

David Ranieri
David Ranieri

Reputation: 41055

#1

Element *ptr1 = malloc(sizeof(ptr1)); is wrong, you want to allocate space with the size of an Element, not with the size of a pointer to that Element,

Change to

Element *ptr1 = malloc(sizeof(*ptr1));

#2

Element *ptr2 = malloc(sizeof(Element));

You are using the typedef (an alias of struct Element), that's fine.


#3

Element *ptr3 = (Element*) malloc (sizeof(Element));

Take a look to Do I cast the result of malloc?


You can also use:

Element *ptr4 = malloc(sizeof(struct Element));

even if struct Element is typedefed.

Upvotes: 1

Related Questions