Dimannn
Dimannn

Reputation: 73

Strange const char* behaviour

GetTypeName is std::string, the following code

printf("%#x\n", proto->GetTypeName().c_str());
printf("%s\n", proto->GetTypeName().c_str());
const char *res = proto->GetTypeName().c_str();
printf("%#x\n",res);
printf("%s\n",res);

produces this output:

0x90ef78
ValidTypeName
0x90ef78
ю■ю■ю■ю■ю■ю■ю■ю■ю■ю■ю■ю■ю■ю■ю■ю■ю■ю■ю■ю■ю■ю■ю■ю■ю■ю■ю■ю■←ЬЬQщZ

addresses are always the same; the following code (lines are exchanges)

const char *res = proto->GetTypeName().c_str();
printf("%#x\n",res);
printf("%s\n",res);
printf("%#x\n", proto->GetTypeName().c_str());
printf("%s\n", proto->GetTypeName().c_str());

produces this output, addresses are always different:

0x57ef78
  Y
0x580850
ValidTypeName

What am I doing wrong?

strlen(res)

returns invalid size, so I can't even strcpy.

Upvotes: 3

Views: 148

Answers (1)

jcoder
jcoder

Reputation: 30035

YourGetTypeName function is returning an std::string and you are calling c_str to get a pointer to the internal data in that string.

As it's a temporary the std::string you return will be deleted at the end of the statement

const char *res = proto->GetTypeName().c_str();

But you still have res pointing to the now deleted data.

Edit: Change your code to something like :-

const std::string& res = proto->GetTypeName(); 

and call .c_str() on that string in the printf like this :-

printf("%#x\n",res.c_str());
printf("%s\n",res.c_str());

Assigning a temporary to a reference extends the lifetime of that temporary to be the same as the lifetime of the reference...

Better still, just use std::string and iostream for printing and stop messing about with low level pointers when unnecessary :)

Upvotes: 5

Related Questions