0

I have two arrays of strings called name and subject. I want to have another array of strings whose elements are obtained by concatenating the string of the first array with the string with the same index of the other array. The new array should be the output of a function.

Here I give a code sample, but I am unable to compile due to getting errors. I have also seen this question but I am unable to use it.

Can anyone give me a hint on how to solve this without dynamic allocation and also with dynamic allocation?

#include <stdio.h>
#include <string.h> 
const int MAX = 4;
char* concancate_string(char* name,char* subject);

int main () {

char* name[] = {
  "michel",
  "sam",
  "roy",
  "romi"
};
char* subject[] = {
  "physics",
  "math",
  "chemistry",
  "biology"
};
char* p[];
p=concancate_string(name,subject);
for ( int i = 0; i < MAX; i++) {
      printf("name and subject[%d] = %s\n", i, name[i] );
}

return 0;

}

char* concancate_string(char* name,char* subject)
{
    for ( int i = 0; i < MAX; i++) {
      strcat(name[i]," : ");
      strcat(name[i],subject[i]);
    }
    return name;
}


resulted output array:
{
 "michel : physics",
 "sam : math",
 "roy : chemistry",
 "romi : biology"
} 
1
  • 1
    Without dynamic allocation it's impossible IMO. Commented Feb 14, 2019 at 9:40

3 Answers 3

2

Here's my attempt with dynamic allocation:

char **concancate_string(const char *name[], const char *subject[], size_t n) {
    char **destin = malloc(n * sizeof *destin);
    for (int i = 0; i < n; i++) {
        destin[i] = malloc(strlen(name[i]) + strlen(subject[i]) + 3 + 1); // add space for " : " and terminating '\0'
        sprintf(destin[i], "%s : %s", name[i], subject[i]);
    }
    return destin;
}

Remember to all free(destin[k]) and free(destin).

See code running on https://ideone.com/3Qb7v1

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

3 Comments

Is sizeof *destin equivalent to sizeof (char*)?
@FrancescoBoi: in this case, yes. I find it is better to use the object itself rather than the type.
Nice answer congrats!
2

First of all, this declaration doesn't work:

char* p[]; // how much stack memory should the compiler reserve?
p=concancate_string(name,subject); // can't assign to an array

Instead, do this:

char **p = concancate_string(name, subject); // you can assign to pointers, though

Also this signature is wrong:

char* concancate_string(char* name,char* subject);

It's taking and returning arrays of char*, not single char*, so it should be:

char **concancate_string(char **name, char **subject);

Furthermore, you can't concatenate to a pointer that you assigned a string literal to. Those point to your program's binary, which is readonly. Instead, the function should look like this:

char **concancate_string(char **name, char **subject)
{
    char **pointers = malloc(MAX * sizeof(char*));
    for (int i = 0; i < MAX; i++) {
        pointers[i] = malloc(strlen(name[i]) + strlen(subject[i]) + 4);
        sprintf(pointers[i], "%s : %s", name[i], subject[i]);
    }
    return pointers;
}

Note how we're allocating an array for the pointers, then allocate memory for every single string, then use sprintf to assemble them (you could also use strcpy and strcat, of course).

Finally, your print is wrong. You make your p, but instead of printing that, you print name. It should instead be:

printf("name and subject[%d] = %s\n", i, p[i]);

And when you're done, the memory should be freed:

for (int i = 0; i < MAX; i++) {
    free(p[i]);
}
free(p);

My suggestion to you is to write your programs one part of the time, only starting with the next part when the last part is tested and works well. If you just write the entire program without testing and then it doesn't work because there's errors all over the place, it becomes much harder to find them.

2 Comments

thanks. Could you explain me why we need double pointer for passing and returning string array to and from function? Also Is we can do same one without dynamic allocation? @Blaze
@ray123 a string itself is represented as a char*, so if you have a whole array of it, then that's an array of char*, so a *char[]. You can write *name[] in the signature instead of **name (the result is the same), but that doesn't work for return type, that has to be **concancate_string because you can't return strings. Can it be done without dynamic allocation? Well, you could have fixed buffers on the stack and copy the strings there, but that would be quite a kludge and have its own caveats, so I'd say it wouldn't solve the same task anymore.
1

If you can assume a maximum length of each string then there is no need to use dynamic allocation. In the example below (which compiles and run) I assumed each string has a length of 100 (99 usable characters plus the \0 character).

So I defined an array using your MAX constant and 100 as char result[MAX][100] = {0};. {0} initializes all the elements to 0 (this initialization works only with 0. Then I passed this new array to the function. Note that you were defining the function parameter as char* name which means a string: you want to pass an array of strings: I redefined as concancate_string(char* name[], char* subject[], char out[MAX][100]): note the difference.

Strings are simply concatenated with strcat. There is also another function strncat which allows you to specify the max number of char to copy.

#include <stdio.h>
#include <string.h>
const int MAX = 4;
int concancate_string(char* name[], char* subject[], char out[MAX][100]);

int main () {
  char result[MAX][100] = {0} ;
  char* name[] = {
    "michel",
    "sam",
    "roy",
    "romi"
  };
  char* subject[] = {
    "physics",
    "math",
    "chemistry",
    "biology"
  };
  int p=concancate_string(name, subject, result);
  for ( int i = 0; i < MAX; i++) {
    printf("%s\n", result[i] );
  }

  return 0;

}

int concancate_string(char* name[], char* subject[], char out[MAX][100])
{
  for ( int i = 0; i < MAX; i++) {
    strcat(out[i], name[i]);
    //printf("%s\n", out[i] );
    strcat(out[i], " : ");
    //printf("%s\n", out[i] );
    strcat(out[i], subject[i]);
    //printf("%s\n", out[i] );
  }
  retur

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.