Trying to sum-up all the discussions, it looks like you will never find a suitable dolution because ... your requirements are in cotraddiction.
- You want you class to behave as ats::string
- std::string behave as a value but
- a value does not "change" when accessed but (think to c = a+b: do you expect a and b to change their value ??) ...
- when accessing your "value" you want to change it.
If what I summed up collecting all the peaces (suggestion: edit your question otherwise all the answerer will risk to be lost) is correct you are in trouble with 3 & 4 (note the 3. derives from the concept of "assignment", and you can do noting to change it, while 4. comes from you directly)
Now, I can try to reverse-engineer your psychology (because you didn't provide good information about what your class represent and why you cannot "extend" a string) I can find
two possibility neither of which will fit all the above requirements.
Store a string into your class and make your class to behave as a std::string. There are threee ways to come to this point:
a. embed a string and make your class to decay to it:
essentially your class must contain
.
operator std::string&() { return my_string; } //will allow l-value assignments
operator const std::string&() const { return my_string; } //will allow r-value usage
const char* c_str() const { return my_string.c_str(); }
b. derive from std::string. In fact that's like having an anonymous my_string in it, which "decay" operations implicit. Not that different as above.
c. embed or privately derive, and rewrite the std::string interface delegating the std::string functions. It's just a long typing to get exactly the b. result. so what the f..k? (this last question is dedicated to all the ones that believe a. or b. will break encapsulation. c. will break it as well, it will only take longer!)
- Don't store a string, but just get it as a result from a calculation (the "lookup" you talk about, not clarifying what it is).
In this last case, what you need is a class that decay automatically into std::string as a value.
So you need, in your class
operator std::string() const { return your_lookup_here; }
note that const is necessary, but there is no need to modify your class inner state, since the resulting string is not stored.
But this last solution has a problem with const char*: since the string is temporary, until you don't assign it, its buffer is temporary as well (will be destroyed) so decaying into const char* to assign the pointer is clueless (the pointer will point to a dead buffer).
You can have a
const char* c_str() const { return std::string(*this).c_str(); } //will call the previous one
but you can use this only into expressions or a pass-through parameter in function calls (since the temporary will exist until the evaluating expression is fully evaluated), not in an assignment towards an l-value (like const char* p; p = myclassinstace.c_str(); )
In all of the above cases (all 1.) you also need:
myclass() {}
myclass(const std::string& s) :my_string(s) { ... }
myclass(const char* s) :my_string(s) { ... }
or - in C++11, just
template<class ...Args>
myclass(Args&&... args) :my_string(std::forward<Args...>(args...)) {}
In case 2., instead of initialize the not existent my_sting, you should use the arguments to set what you will look up (we don't know what it is, since you did not tell us)
Hope in all these option you can find something useful.
std::string?const charValue =is a pretty strong requirement ...