Reputation: 3064
I'm trying to return a data structure from a function named urlTokener
where in the data structure one member is an array of type char*
and the other is int. When I print the values of the array in the function urltokener
I get the correct type, but I see that in the main function where the returned data structure is used, the array doesn't contain the right values as the output is not right(not the same as in the function). It seems the function is not returning the data structure correctly. Could you please check and say what I'm doing wrong in the following code?
#include <string.h>
#include <stdio.h>
struct tokenDetail
{
char* theArray[256];
int sizeOfArray;
};
tokenDetail urlTokener(const char *,char* );
void main()
{
// String to be splitted.
const char* url="/v1/AUTH_abb52a71-fc76-489b-b56b-732b66bf50b1/images?limit=1000&delimiter=/&format=xml" ;
tokenDetail newdetails;
newdetails=urlTokener(url,"?");
for (int i=0;i<newdetails.sizeOfArray;i++)
{
printf("This is in main where size is %d and the value %s\n",newdetails.sizeOfArray,newdetails.theArray[i]);
}
}
tokenDetail urlTokener(const char* urlLine,char* delimiter)
{
char urlArray[256];
strncpy(urlArray, urlLine, sizeof(urlArray));
tokenDetail details;
unsigned int index = 0;
details.theArray[index] = strtok(urlArray, delimiter);
while(details.theArray[index] != 0)
{
printf("This is in function %s\n",details.theArray[index]);
++index;
details.theArray[index] = strtok(0, delimiter);
}
for (int i=0;i<index;i++)
{
printf("This is in function 2nd time %s\n",details.theArray[i]);
}
details.sizeOfArray=index;
return details;
}
Please note : I'm doing it for c++, but I'm not allowed(by the person who gave me this task) to use namespace std, and library string. Which is why the code is similar to C. Because of this limitation I'm confused whether to tag it C or C++. So I tagged it in both c and c++. May be you could decide yourself.
Upvotes: 2
Views: 179
Reputation: 153909
You're filling the array with pointers returned from strtok
, which in
turn are pointers into your urlArray
, a local variable, which ceases
to exist once you return from the function.
Is this C or C++? You've set both labels, and the solution is
different. In C++, the obvious solution is to replace the char*
in
tokenDetail
with std::string
. In C, it's a bit more complicated.
You have dynamically allocate the strings in your struct (using the
non-standard but widely available strdup
), and require the client to
free them. The usual solution here is to return a pointer to a
dynamically allocated TokenDetail
, and a freeTokenDetail
function
which the client is required to call on the returned pointer. This
gives you total freedom in how you do your allocations and frees. (The
usual solution is, in fact, to only provide a forward declaration of
TokenDetail
to the clients, and to provide functions which they have
to call to access its elements.)
Upvotes: 3
Reputation: 11028
The problem here is not that tokenDetail
needs any handwritten copy constructor, destructor or assignment operator, which it doesn't. The problem is that the local variable urlArray
is destroyed when you leave urlTokener()
, so the positions pointed to by the elements of details.theArray
become invalid. And, of course, the same happens with the returned tokenDetail
, which is a copy of it.
Upvotes: 2
Reputation: 258558
You didn't implement the copy constructor, destructor or assignment operator.
Because you return by value, the copy constructor is called on return details;
, but the default one only does a shallow copy, so the field char* theArray[256];
isn't copied properly.
Upvotes: 0