Programming language more modern than C sport great libraries of functions, or “methods.” Java has so many I doubt that a single programmer knows them all. In C, however, when a function is absent (and a lot of them are, comparably), you must code your own. Such is the case with building a string.
The C language features the strcat() function, which sticks one string onto the end of another. To continue building the string, you use additional strcat() functions, sometimes several in a row. When this situation happened to me recently, I decided to craft my own string building function, something that’s readily available in other programming languages.
The function I created is called concatenate(). It consumes a number of strings, sticks them all together, then returns a single string. Because the number of strings is variable, I use a variable argument list in the function’s definition:
char *concatenate(int v, ...)
Integer v
represents the number of arguments, which appear as ...
in the declaration. You can read more about variable argument lists in this blog post.
Here is sample code that demonstrates my concatenate() function:
2025_01_04-Lesson.c
#include <stdio.h> #include <stdlib.h> #include <string.h> #include <stdarg.h> char *concatenate(int v, ...) { va_list argc; int x; char *r,*temp; va_start(argc,v); for(x=0; x<v; x++) { temp = va_arg(argc,char *); if( x==0 ) { r = malloc( sizeof(char) * strlen(temp) +1 ); if( r==NULL ) return("NULL"); strcpy(r,temp); } else { r = realloc(r, sizeof(char) * (strlen(r) + strlen(temp)) +1 ); if( r==NULL ) return("NULL"); strcat(r,temp); } } /* clean up */ va_end(argc); return(r); } int main() { char *a,*b,*c; a = concatenate(4,"alpha ","beta ","gamma ","delta"); printf("%s\n",a); b = concatenate(1,"Hello, world!"); printf("%s\n",b); c = concatenate(6,"f","o","o","b","a","r"); printf("%s\n",c); /* clean-up */ free(a); free(b); free(c); return 0; }
The stdarg.h
header is required to manipulate the variable argument list and define the va_start(), va_arg() and va_end() macros.
The main() function calls the concatenate() function three times. Each statement uses differently formatted strings and a different number of arguments. The function staples strings together as-is; no spaces are inserted between them.
The concatenate() function obtains the argument count from the va_start() macro. This value, saved in variable v
, is used in a for loop to process each of the arguments. The char pointer variable temp
references each string: temp = va_arg(argc,char *);
An if decision determines when the first string is added. If so, the malloc() function allocates storage for the string, then copies it into the allocated buffer, r
. Otherwise, the else condition uses the realloc() function to reallocate storage for the next string plus the existing string. The strcat() function sticks the string to the end of the string being built and referenced by char pointer variable r
.
After the string is built, the va_end() function cleans up the variable argument list. Variable r
, referencing the built string, is returned to the caller.
Here’s a sample run:
alpha beta gamma delta
Hello, world!
foobar
This code works, thanks to variable argument lists. The value returned is a pointer, so it need not be made static. In my program, separate pointers store the returned strings’ addresses, which are freed before the program quits.
I’m quite pleased with my concatenate() function and welcome its addition to my personal string library. I hope you also appreciate that C lets you create such functions when needed. While programmers in other languages may be annoyed at this type of task, I think it’s one of the better aspects of C programming.
The thing I find most surprising and frustrating about C is that there is no major, well-known and popular repository for libraries. In other major languages something like this would be uploaded to some site which everyone knows about and would instantly turn to. There would probably be many libraries for any given field but the one which was generally considered to be the best would soon become the most popular and become the de-facto standard. There are plenty of excellent C libraries around but they are scattered all over the place, and with little way of gauging their popularity and quality.
I wholeheartedly agree! It would make coding projects go so much easier if we had a major repository for common routines and libraries.
Maybe you should start one . . . !
Or a simpler option, add a page to this site linking to any you think are useful and reliable.
I may do that!