Static strings: string or char*?

Started by
16 comments, last by Trap 19 years, 4 months ago
no, you'll get a pointer to a const character array, they just happen to be used as strings, thats all [smile]
Advertisement
Quote:Original post by _the_phantom_
no, you'll get a pointer to a const character array, they just happen to be used as strings, thats all [smile]


No, string literal is not an l-value so a temporary std::string object will be created and bound to the reference.
wanna run that by me again... why would passing a pointer to a character array get promted to an std::string? They arent even the same time, why on earth would the compiler automagically do that promotion? If I try to write to the constant char array then I'd expect the compiler to scream at me about it, not do silly autopromtion tricks... unless someone has invented the DWIM switch for the compilers and not told me [wink]
Because the string class has a constructor that takes a char const*. Now, as every "good" C++ book teaches you, a C++ compiler can make at most one implicit casts to a type, so since there is an available constructor, the compiler can implicitly cast the char const* to a std::string by calling the appropriate constructor.

In time the project grows, the ignorance of its devs it shows, with many a convoluted function, it plunges into deep compunction, the price of failure is high, Washu's mirth is nigh.

hmmm yes I follow that and have used it in the past [smile]

I think I see the issue here, I might well have misread the intent of MagicScript's post, I'm now thinking that he ment if you define the function as taking a const std::string & and pass it a const char * then you'll get a string, which ofcourse is correct, however I thought at the time that he ment if you passed and wanted a const char * then it would be a string anyways (as in changeable via the C lib. str*() functions), thus when fallenang3l brought std::strings into the mix it all got rather confusing [smile]
Hmmm, as for that const string & question... I didn't invent it myself, source: Game Programming Gems #2, author: Andrew Kirmse, LucasArts. (though I did invent that: string foo(_blablabla), sure, in this case, in one possible situation I was wrong, but read to the end of my post)

Kirmse explains that for this kind of code:

void Function(const std::string &str) {  ... }Function("Hello");


calling Function would call constructor (with parameter const char *), which often calls malloc(), strlen and memcpy(), and when str is going to be destructed, obviously free() is going to be called and in implementaton which uses reference counted strings, Slow Things will happen... In this situation we've just duplicated the string in memory cause it's already in program memory segment. And dynamic allocation is slow and can be very wastefull when inproperly used, especially in main loop or often called functions.

Ok, you may say that when we pass some const char * that's generated at runtime ie. typed by the user, then it won't be such wastefull. Well, I honestly say that depends on the situation. If you use that string just for some basic operation ie. searching texture in map of textures, then std::strings obviosly create unnecessary overhead. But if you do some sort of parsing... sure, why not use std::strings, in this case it would be the same as using that second method.

And one last thing: when dealing with COM interface writing or when you need to create DLL that can be used in other programming languages, then passing std::strings as arguments is forbidden, you must use const char * (though you can later initialize some local string with that argument, now you know why I've written that second case...)
the main thing is, if you want efficiency, you should pass around 1 or the other of the 2 in almost all cases, so you don't have to promote and wrap, or lock down for conversion ...

basically, either use const char * in as many places as possible (basically anywhere that is not supposed to modify the string) OR use const string & in as many places as possible ... but don't use both ...

of course for things which need to do modification, they should take string &, char *, or char ** depending on their expected needs ... it is silly to take a char * as input to a function that's going to do work using a string, and then copy back the resulting char * ... and it's silly to take string& when your algorithm needs to copy into a character buffer, modify, and then assign back ...
MS VC7 => sizeof(std::string)==28
G++ 3.4.2 => sizeof(std::string)==4 !

How does this work? G++ allocates 12 additional bytes directly in front of the char[] that stores the actual string to store all management data.
So std::string doesn't have to have a big overhead over raw char*.

This topic is closed to new replies.

Advertisement