Copying Command Line Arguments Into an Array

16,145

Solution 1

You're not allocating or copying the terminating NULL characters:

This line needs to be changed to this for the NULL.

array[i] = malloc((strlen(*(argv + i)) + 1) * sizeof(char));   

And the loop should be changed to this:

for(j = 0; j <= strlen(*(argv + i)); j++){ 

Also, the code can be better optimized if you saved the result of the strlen() call since you call it in so many places.

Try the loop as this:

// For each element allocate the amount of space for the number of chars in each argument
for(i = 0; i < argc; i++){

    int length = strlen(argv[i]);

    array[i] = malloc((length + 1) * sizeof(char));
    int j;

    // Cycle through all the chars and copy them in one by one
    for(j = 0; j <= length; j++){
        array[i][j] = argv[i][j];
    }

}

Solution 2

first you need to allocate a vector of char*, not just a char*

char **array;

array = malloc(sizeof(char*)*(argc+1)); // plus one extra which will mark the end of the array

now you have an array[0..argc] of char* pointers

then for each argument you need to allocate space for the string

int index;
for (index = 0; index < argc; ++index)
{
   arrray[index] = malloc( strlen(*argv)+1 ); // add one for the \0
   strcpy(array[index], *argv);
   ++argv;
}
array[index] = NULL; /* end of array so later you can do while (array[i++]!=NULL) {...} */
Share:
16,145
Matt
Author by

Matt

Updated on June 04, 2022

Comments

  • Matt
    Matt almost 2 years

    For a program, I would like to make an array copy of the arguments sent in by command line using malloc().

    So for example if I do ./a.out one two three I want an array with {a.out, one, two, three} in it.

    However, I have some issues getting my program to work. Here's what I have:

    static char** duplicateArgv(int argc, char **argv)                                                                                                                                                         
    {                                                                                                                                                                                                                                                                                                                                                                                       
        char *array;                                                                                                                                                                                                                                                                                                                                                               
        int j = 0;                                                                                                                                                                                        
    
        // First allocate overall array with each element of char*                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                           
        array = malloc(sizeof(char*) * argc);                                                                                                                                                       
        int i;                  
    
        // For each element allocate the amount of space for the number of chars in each      argument                                                                                                                                                              
        for(i = 1; i < (argc + 1); i++){                                                                                                                                                                      
            array[i] = malloc(strlen(*(argv + i)) * sizeof(char));                                                                                                                                        
            int j;       
    
            // Cycle through all the chars and copy them in one by one                                                                                                                                                                                 
            for(j = 0; j < strlen(*(argv + i)); j++){                                                                                                                                                     
                array[i][j] = *(argv + i)[j];                                                                                                                                                                                                                                                                                                                                                       
            }                                                                                                                                                                                             
    
        }                                                                                                                                                                                                 
    
        return array;
    
    }
    

    As you might imagine, this doesn't work. I apologize ahead of time if this somehow totally doesn't make sense, as I just started learning about pointers. Also, I'm not quite sure how to write code to free up every element in the *array after I do what I need to the copy.

    Could anyone give me some tips on what I should look into to make it do what I want?

    Thanks for any help!

  • Matt
    Matt over 12 years
    I tried to print it with while(*array){printf("%s", *array++);}, but I don't get any output (I get a seg fault). Hmm...
  • Mysticial
    Mysticial over 12 years
    You also need to change char *array; to char **array; Is it still not working?
  • Mysticial
    Mysticial over 12 years
    I overlooked one more thing: Your loop indexing should start from 0 and not 1. I've edited it into the answer.
  • Matt
    Matt over 12 years
    I changed it and this works. Thank you so much! However, I am wondering why you used argv[i][j] and strlen(argv[i]) rather than strlen(*(argv +i))? I thought the expressions were equivalent.
  • Mysticial
    Mysticial over 12 years
    I made that change because I wasn't sure of the precedence between * and []. Then I just copied and pasted it wherever I found it.
  • Matt
    Matt over 12 years
    EDITED: Nevermind I see what you're saying. Thanks again for all your help!
  • Mysticial
    Mysticial over 12 years
    You had *(argv + i)[j]. I wasn't sure if it would be parsed as (*(argv + i))[j] or *((argv + i)[j]). And it makes a difference in this case.
  • Matt
    Matt over 12 years