Home > Mobile >  C string struct with mem allocation included
C string struct with mem allocation included

Time:10-12

I am working with a bunch of strings for logging. I want to refactor my code and make a new struct that combines the char, its length and allocated size. The idea is to make my internal string operations smoother and the code nicer to read, whilst assigning each string its own max allocated memory to keep the usage to a minimum but prevent stack overflow. I made this simple example:

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


typedef struct 
{
  char *str;
  int size;
  int max;
} Text;

void defText(Text *text, int max)
{
  text->str=(char*) malloc(max * sizeof(char));
  text->str="";
  text->max=max;
}


int main() {
    Text *a;
    defText(a,50);
    a->str="Test all you want";
    printf("OUT: %s %zu %lu",a->str,strlen(a->str),sizeof(a->str));
    return 0;
}

The function defText initializes and allocates memory. However, when I check the sizeof the char in my struct, I always get 8, no matter what I set in defText. Is this kind of struct handling strings and their properties together even possible? If so, what is wrong here?

CodePudding user response:

There are several problems in your code, this is an example that cleans up these problems:

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

typedef struct 
{
  char *str;
  // you could use size to keep track of the strlen. That's particularly
  // desirable if you find yourself calling strlen "a lot", since that
  // function recalculates the length every time it's called
  int size;
  int max;
} Text;

void defText(Text *text, int max)
{
  // no need to cast the return of malloc. In fact, sizeof(char) is defined by
  // the standard to be 1 so you could take that out also.
  text->str=malloc(max * sizeof(char));
  // `=` is not the proper way to write strings in C, you must use strcpy
  // or something similar. It looks like here you're simply trying to
  // create an empty string.
  //text->str="";
  // per @JohnBollinger's comment, the best thing to do here to create
  // an empty string is simply set to the first byte to the NUL
  // terminator.
  text->str[0] = '\0';
  text->max=max;
}


int main() {
    Text a;  // store this in automatic memory, now the object exists without having to malloc
    defText(&a,50); // Use & to pass the address of a to defText

    // as mentioned, this is not the proper way to write data to a string in
    // C. What you've done here is create a memory leak and point a.str to
    // the string literal "Test all you want". Use strcpy (or similar) to
    // write that string into the data you actually malloc'ed (using the dot
    // operator now since `a` is no longer a pointer)
    //a->str="Test all you want";
    strcpy(a.str, "Test all you want");
    // a.str is a pointer, and will always be 8 bytes on your system no matter
    // the size of the memory it points to
    printf("OUT: %s %zu %zu",a.str,strlen(a.str),sizeof(a.str));

    // clean up allocated memory. Since we're about to exit, there's
    // really no need to do this here (the OS will reclaim all allocated
    // memory when the process ends), but if you're writing a more
    // involved, long-running program, you need to be sure to handle
    // memory allocations and deallocations appropriately as needed
    free(a.str);

    return 0;
}

Demo

CodePudding user response:

The a->str is pointer . the correct answer is sizeof(*(a->str))

  • Related