CONST CORRECTNESS
- Const correctness refers to the use of the C++ const keyword to declare a variable or method as immutable.
- It is a compile-time construct that can be used to maintain the correctness of code that shouldn’t modify certain variables. In C++, you can define variables as const, to mean that they should not be modified, and you can also define methods as const, to mean that they should not modify any member variables of the class. Using const correctness is simply good programming practice.
- Also, provide documentation on the intent of your methods, and hence make them easier to use.
- Ensure that your API is const correct.
Method Const Correctness
- A const method cannot modify any member variables of the class. In essence, all member variables are treated as const variables inside of a const method. This form of const correctness is indicated by appending the const keyword after the method’s parameter list.
- To advertise the fact that the method will not change the state of the object. As just discussed, this is helpful documentation for users of your API.
- To allow the method to be used on const versions of an object. A non-const method cannot be called on a const version of an object.
- Declare methods and parameters as const as soon as you can. Trying to retrofit const correctness into an API at a later date can be a time-consuming and frustrating activity.
int Remove(const std::string &str); // Const referance argument
bool Has(const std::string &str) const; // Const referance argument and return type const
int GetSize() const; // Return type const
- It is pointless to return a const value from a function
Parameter Const Correctness
- Use of the const keyword can also be used to indicate whether you intend for a parameter to be an input or an output parameter,
std::string StringToLower(const std::string &str);
- Now the compiler will enforce the fact that the function StringToLower() will not modify the string that the user passes in.
- When passing a reference or pointer into a const method, think about whether that parameter can be declared const too.
Return Value Const Correctness
- When returning the result of a function, the main reason to declare that result to be const is if it references an internal state of the object
- If returning a result by value, then it makes little sense to specify it as const because the returned object will be a copy, and hence hanging it will not affect any of your class’s internal state.
- Alternatively, if return a pointer or reference to a private data member, then you should declare the result to be const, as otherwise, users will be able to modify your internal state without going through your public API.
- In this case, you must also think about whether the returned pointer or reference will survive longer than your class. If this is possible, use smart pointers.
- For to return the result of a function by value rather than const reference.
// return by value
std::string GetName() const
{
return mName;
}
// return by const reference
const std::string &GetName() const
{
return mName;
}
- In general, recommend returning the result by value as it is safer.
- However, may prefer the const reference method in a few cases where performance is critical. Returning by value is safer because you don’t have to worry about clients holding onto references after your object has been destroyed, but also because returning a const reference can break encapsulation.
- The client can always cast away the constness of the reference and then modify the underlying private data member directly, such as in the following example:
// get a const reference to an internal string
const std::string &const_name = object.GetName();
// cast away the constness
std::string &name const_cast<std::string &>(const_name);
// and modify the object’s internal data!
name.clear();
References
- API Design for C++ Book by Martin Reddy
No comments:
Post a Comment