const overloaded operator[] function and its invocation
I define two versions of overloaded operator[]
function in a class array
. ptr
is a pointer to first element of the array
object.
int& array::operator[] (int sub) {
return ptr[sub];
}
and
int array::operator[] (int sub) const {
return ptr[sub];
}
Now, if I define a const object integer1
the second function can only be called..... but if I make a non-const object and then invoke开发者_运维问答 as below:
cout << "3rd value is" << integer1[2];
which function is called here?
In your second example, the non-const version will be called, because no conversion is required, and a call that requires no conversion is a better match than one that requires a conversion.
Ultimately, however, you have a basic problem here: what you really want is behavior that changes depending on whether you're using your object as an rvalue or an lvalue, and const
doesn't really do that. To make it work correctly, you normally want to return a proxy object, and overload operator=
and operator T
for the proxy object:
template <class T>
class myarray {
T *ptr;
class proxy {
T &val;
proxy &operator=(proxy const &p); // assignment not allowed.
public:
proxy(T &t) : val(t) {}
operator T() const { return val; }
proxy &operator=(T const&t) { val = t; return *this; }
};
proxy const operator[](int sub) const { return proxy(ptr[sub]); }
proxy operator[](int sub) { return proxy(ptr[sub]); }
// obviously other stuff like ctors needed.
};
Now we get sane behavior -- when/if our array<int>
(or whatever type) is const, our operator[] const
will be used, and it'll give a const proxy
. Since its assignment operators are not const, attempting to use them will fail (won't compile).
OTOH, if the original array<int>
was not const, we'll get a non-const proxy, in which case we can use both operator T
and operator=
, and be able to both read and write the value in the array<int>
.
Your const version should return const int&
not int
, so that the semantics are just the same between the two functions.
Once you've done that, it doesn't matter which one is used. If the const
version has to be used because your object has a const context, then it will be... and it won't matter as you're not trying to modify anything. Otherwise, it'll use the non-const
version... but with just the same effect.
精彩评论