Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

What's the correct way to use const in C++?

const correctness has me somewhat confused.

What rule of thumb do you use to decide when something should be const or not?

e.g. consider this example

class MyClass
{
  string ToString(); // this one?
  const string& ToString(); // or this? 
  const string& ToString() const; // or this?

  char* ToString(); // What about this?
  const char* ToString(); // or this?
  const char* ToString() const; // or this?
  const char const* ToString(); // Is this legal?
  const char const* ToString() const; // how about this?
  char const* ToString();  // or even this?
};

Const can get really confusing.

What would be the difference between all these ToString methods?

If I understand correctly, the first one returns a new string object that can be modified if need be. The second one returns a constant reference maybe it should be string const& ToString(). The third one is probably a nonsense because references are always constant is that correct?

Thought I'd throw the old char* versions in there for comparison as I do have methods that return object pointers and I'm not sure whether they should be const or not.

I guess I'm just trying to understand the limitations and benefits of const correctness and how to decide up front whether something should be const or not and how to correctly apply const since placing const in different places changes the meaning.

EDIT: also, how do I deal with that '... discards qualifiers'. What does that actually mean?

like image 802
hookenz Avatar asked Nov 15 '22 06:11

hookenz


1 Answers

Where you use const depends on the purpose of the function. As James suggests in his comment (which is worth putting as an answer), put const anywhere you can:

If the function is intended to modify state within it's object instance, don't put const at the end of the signature.

If the function is intended to modify one of it's reference or pointer parameters, don't put const on the parameter.

If the variable referenced by a pointer or reference should be modified, don't put const on the type (remember, const applies to the part of the definition immediately prior).

If the returned reference/pointer references a variables that should not be changed by the received, do put const on the type.

Answering the examples given in the question is impossible without knowing the purpose of the functions. My tendency would be to use string ToString() const and char* ToString() const, with very clear documentation on who is responsible for deleteing the char*.


As an extra note, const char* and char const* are identical (pointer to unmodifiable characters). char* const, on the other hand, is an unmodifiable pointer to modifiable characters.

like image 133
Zooba Avatar answered Dec 16 '22 15:12

Zooba