Thread: adding a copy of a string (not pointer) to vector (struct)

  1. #1
    Registered User
    Join Date
    Jul 2019
    Posts
    8

    adding a copy of a string (not pointer) to vector (struct)

    Hello, I made a vector struct that I tested and thought was working like I wanted but now it does something that I don't want.

    my vector.h
    Code:
    typedef struct vector {
        void **data;
        int capacite;
        int nbData;
    } vector;
    
    
    void vector_init(vector *);
    int vector_total(vector *);
    void vector_resize(vector *, int);
    void vector_add(vector *, void *);
    void vector_set(vector *, int, void *);
    void *vector_get(vector *, int);
    void vector_delete(vector *, int);
    void vector_empty(vector *);
    void vector_print(vector *);
    void vector_free(vector *);
    some parts of my vector.c (don't to flood with codes)
    Code:
    void vector_init(vector *v){
        v->capacite = capacite_ini;
        v->nbData = 0;
        v->data = calloc(v->capacite,sizeof(void *));
        //v->data = malloc(sizeof(void *) * v->capacite);
    }
    
    void vector_add(vector *v, void *item){
        if (v->capacite == v->nbData)
            vector_resize(v, v->capacite * 2);
            v->data[v->nbData++] = item;
    }
    In my main file, I'm reading words from a file and adds them to my vector but I'm adding a pointer so all the ''words'' in my vector are the same and change.

    my main:
    Code:
    char mot[30];
    
    char c;
    int j=0;
    while((c = fgetc(fIN)) != EOF){
        if(c == '\n')
            continue;
        if(j != 0 && c == ' '){
            mot[j]='\0';
            vector_add(&vector_dut,mot);
            j=0;
            mot[0] = '\0';
            vector_print(&vector_dut);
        }
            mot[j]=c;
            j++;
    }
    ...
    I know in other language, it would have been possible to do vector_dut(new String temp)...

    thanks in advance!

  2. #2
    and the hat of int overfl Salem's Avatar
    Join Date
    Aug 2001
    Location
    The edge of the known universe
    Posts
    39,660
    > v->data[v->nbData++] = item;
    You need to malloc and copy the data.

    All you have at the moment is a bunch of pointers, all pointing to mot.

    So whatever is in mot, is what gets printed 'n' times.
    If you dance barefoot on the broken glass of undefined behaviour, you've got to expect the occasional cut.
    If at first you don't succeed, try writing your phone number on the exam paper.

  3. #3
    Registered User
    Join Date
    Jul 2019
    Posts
    8
    Quote Originally Posted by Salem View Post
    > v->data[v->nbData++] = item;
    You need to malloc and copy the data.

    All you have at the moment is a bunch of pointers, all pointing to mot.

    So whatever is in mot, is what gets printed 'n' times.
    ok, I'll test this now. I tried doing strcpy (without malloc) but it didn't work.

  4. #4
    Registered User
    Join Date
    Jul 2019
    Posts
    8
    Code:
    void vector_add(vector *v, void *item){
        if (v->capacite == v->nbData)
            vector_resize(v, v->capacite * 2);
        v->data[v->nbData++] = (char*) malloc((30)*sizeof(char));
    
    
        strcpy(v->data[v->nbData],item);
    }
    I changed my vector_add but it gives me a segmentation error when I try to to strcpy.

    From what you said (and understand), I malloc the array of my array(data) so that I can copy the new ''word'' in it.

  5. #5
    and the hat of int overfl Salem's Avatar
    Join Date
    Aug 2001
    Location
    The edge of the known universe
    Posts
    39,660
    Like so
    Code:
        v->data[v->nbData] = (char*) malloc((30)*sizeof(char));
        strcpy(v->data[v->nbData],item);
        v->nbData++;
    If you dance barefoot on the broken glass of undefined behaviour, you've got to expect the occasional cut.
    If at first you don't succeed, try writing your phone number on the exam paper.

  6. #6
    Registered User
    Join Date
    Jul 2019
    Posts
    8
    I found my mistake (a dumb one) I was doing v->data[v->nbData] = (void *) malloc((30)*sizeof(char));

    instead of void void.

    Thanks a lot for the help!

  7. #7
    and the hat of int overfl Salem's Avatar
    Join Date
    Aug 2001
    Location
    The edge of the known universe
    Posts
    39,660
    The actual cast on the result of malloc would be irrelevant at that point.
    If you dance barefoot on the broken glass of undefined behaviour, you've got to expect the occasional cut.
    If at first you don't succeed, try writing your phone number on the exam paper.

  8. #8
    Registered User
    Join Date
    Jul 2019
    Posts
    8
    I know that when I changed char * for void* it worked, I probably forgotmwhich one was char* or void* or I had an another mistake.
    Thanks again for your help!

  9. #9
    and the hat of int overfl Salem's Avatar
    Join Date
    Aug 2001
    Location
    The edge of the known universe
    Posts
    39,660
    Well the real change was changing
    v->data[v->nbData++]
    to
    v->data[v->nbData]

    If you do the ++ before the strcpy, you end up using the wrong pointer for the strcpy.
    If you dance barefoot on the broken glass of undefined behaviour, you've got to expect the occasional cut.
    If at first you don't succeed, try writing your phone number on the exam paper.

  10. #10
    Registered User
    Join Date
    Feb 2019
    Posts
    1,078
    To make a copy of string you can use strdup(), instead of malloc/strcpy. I works exactly as malloc/strcpy, but you don't need to calculate the buffer size.

  11. #11
    C++ Witch laserlight's Avatar
    Join Date
    Oct 2003
    Location
    Singapore
    Posts
    28,413
    Have you considered storing a char** instead of a void**? By using the latter, you presumably want some kind of generic vector, but then you need to change your vector interface to account for the size of objects that it stores, and it becomes even more complicated for strings because you cannot assume that just because each void* points to a char, that that char is necessarily the first char in a string. If you just went with a char** and documented this as being a vector of strings, problem solved.
    Quote Originally Posted by Bjarne Stroustrup (2000-10-14)
    I get maybe two dozen requests for help with some sort of programming or design problem every day. Most have more sense than to send me hundreds of lines of code. If they do, I ask them to find the smallest example that exhibits the problem and send me that. Mostly, they then find the error themselves. "Finding the smallest program that demonstrates the error" is a powerful debugging tool.
    Look up a C++ Reference and learn How To Ask Questions The Smart Way

  12. #12
    TEIAM - problem solved
    Join Date
    Apr 2012
    Location
    Melbourne Australia
    Posts
    1,907
    Code:
    char c;
    int j=0;
    while((c = fgetc(fIN)) != EOF){
    "c" should be declared an int

    What you have done is similar to this FAQ: Question 12.1

  13. #13
    Registered User
    Join Date
    Jul 2019
    Posts
    8
    Quote Originally Posted by laserlight View Post
    Have you considered storing a char** instead of a void**? By using the latter, you presumably want some kind of generic vector, but then you need to change your vector interface to account for the size of objects that it stores, and it becomes even more complicated for strings because you cannot assume that just because each void* points to a char, that that char is necessarily the first char in a string. If you just went with a char** and documented this as being a vector of strings, problem solved.
    This is actually something that I thought about I want to make a generic vector but with the strings it complicates things. At this point, it is a vector of string more than generic.

    Thanks for the info!

  14. #14
    Registered User
    Join Date
    Jul 2019
    Posts
    8
    Quote Originally Posted by flp1969 View Post
    To make a copy of string you can use strdup(), instead of malloc/strcpy. I works exactly as malloc/strcpy, but you don't need to calculate the buffer size.
    I'll test this, thanks!

  15. #15
    Registered User
    Join Date
    Jul 2019
    Posts
    8
    Quote Originally Posted by Click_here View Post
    Code:
    char c;
    int j=0;
    while((c = fgetc(fIN)) != EOF){
    "c" should be declared an int

    What you have done is similar to this FAQ: Question 12.1
    I looked into that and you are right, never thought char ''were'' int, Thanks for the info!

Popular pages Recent additions subscribe to a feed

Similar Threads

  1. Searching string within vector struct C++ 11
    By coffee_cup in forum C++ Programming
    Replies: 6
    Last Post: 11-03-2013, 10:40 PM
  2. 2D vector struct, 1D pointer?
    By motocross1 in forum C++ Programming
    Replies: 5
    Last Post: 01-27-2012, 02:50 PM
  3. copy string by pointer
    By mohsen in forum C Programming
    Replies: 6
    Last Post: 01-25-2012, 11:59 AM
  4. How to copy value from MySQL result to string pointer?
    By fekkesh in forum C Programming
    Replies: 2
    Last Post: 03-12-2009, 08:52 AM
  5. string vector to string pointer manipulation
    By stanlvw in forum C++ Programming
    Replies: 11
    Last Post: 07-16-2008, 01:43 AM

Tags for this Thread