![]() |
const correctness - should C++ prefer const member over non-const?
I define this class:
class foo { std::vector<int>data; public: int operator[](int n) { return data[n]; } int operator[](int n) const { return data[n]; } }; Now in my program I do: foo myFoo; int x = myFoo[123]; .... Should the const version of foo::operator[] be called? I think it should, but my compiler disagrees with me. What's the correct behavior? Why...? -- <\___/> / O O \ \_____/ FTB. http://www.topaz3d.com/ - New 3D editor! |
Re: const correctness - should C++ prefer const member over non-const?
In article <7908dabe-5102-4669-bf68-6cd36bedd6a7
@m74g2000hsh.googlegroups.com>, openglMYSOCKS@artlum.com says... > I define this class: > > > class foo { > std::vector<int>data; > public: > > int operator[](int n) { > return data[n]; > } > int operator[](int n) const { > return data[n]; > } > }; > > > Now in my program I do: > > foo myFoo; > int x = myFoo[123]; > ... > > > Should the const version of foo::operator[] be called? No. > I think it should, but my compiler disagrees with me. The compiler's right. The const version should be called for a const object. The non-const version should be called for a non-const object. If you don't/didn't have a non-const version, then the const version could be called -- but it would be called by convertion the non-const to a const object first. That's fine (in this case) but it's still a conversion. When matching overloaded functions, one that doesn't require a conversion is a better match than one that does require a conversion. Most people want the const version used on the RHS of an assignment, but the non-const for the LHS. To get what that kind of behavior, you normally use a proxy object that overloads operator= and operator T. -- Later, Jerry. The universe is a figment of its own imagination. |
Re: const correctness - should C++ prefer const member overnon-const?
On Oct 30, 6:31*am, blargg....@gishpuppy.com (blargg) wrote:
> > I'm interested in why you think it should call the const version. If it > did, when would it ever call the non-const version? Ok, maybe I oversimplified it. Supposed operator[] returns a reference to the int: int& operator[](int n) { return data[n]; } int& operator[](int n) const { return data[n]; } If the expression is on the RHS of an assignment, should the const version be called? -- <\___/> / O O \ \_____/ FTB. http://www.topaz3d.com/ - New 3D editor! |
Re: const correctness - should C++ prefer const member overnon-const?
On Oct 30, 10:21*am, fungus <openglMYSO...@artlum.com> wrote:
> > Ok, maybe I oversimplified it. Supposed operator[] > returns a reference to the int: > ....and just before the pedants arrive, suppose it's a struct not an int, and I want to access a member of the stuct. my_struct& operator[](int n) { return data[n]; } const my_struct& operator[](int n) const { return data[n]; } Why does the compiler choose the non-const version for the RHS of an expression...? -- <\___/> / O O \ \_____/ FTB. http://www.topaz3d.com/ - New 3D editor! |
Re: const correctness - should C++ prefer const member over non-const?
fungus wrote:
> I define this class: > > > class foo { > std::vector<int>data; > public: > > int operator[](int n) { > return data[n]; Changing this line to this: return data.at(n); is much safer > } > int operator[](int n) const { > return data[n]; > } > }; > > > Now in my program I do: > > foo myFoo; > int x = myFoo[123]; > ... > This should call the non-const operator[] If you had: const foo myFoo; int x = myFoo[123]; then the const version of the operator[] would be used > > Should the const version of foo::operator[] be called? > > I think it should, but my compiler disagrees with me. > > What's the correct behavior? Why...? > |
Re: const correctness - should C++ prefer const member over non-const?
fungus wrote:
> On Oct 30, 10:21 am, fungus <openglMYSO...@artlum.com> wrote: >> Ok, maybe I oversimplified it. Supposed operator[] >> returns a reference to the int: >> > > ...and just before the pedants arrive, suppose it's > a struct not an int, and I want to access a member > of the stuct. > > my_struct& operator[](int n) { return data[n]; } > const my_struct& operator[](int n) const { return data[n]; } > > Why does the compiler choose the non-const version > for the RHS of an expression...? Because your myFoo object is not const |
Re: const correctness - should C++ prefer const member overnon-const?
On Oct 30, 6:41*am, Jerry Coffin <jcof...@taeus.com> wrote:
> > > Should the const version of foo::operator[] be called? > > No. > > > I think it should, but my compiler disagrees with me. > > The compiler's right. Bummer. I've got an object which triggers quite a big internal rebuild when you call the non-const version and I just noticed it's doing a lot of rebuilding because of this assumption. -- <\___/> / O O \ \_____/ FTB. http://www.topaz3d.com/ - New 3D editor! |
Re: const correctness - should C++ prefer const member overnon-const?
On 30 Okt., 10:59, fungus <openglMYSO...@artlum.com> wrote:
> Bummer. I've got an object which triggers quite > a big internal rebuild when you call the non-const > version and I just noticed it's doing a lot of > rebuilding because of this assumption. You can explicitly convert your object to a const version if you don't want the non-const member function to be called in some cases: const foo& myConstFoo = myFoo; int blah = myConstFoo[42]; or something like that. static_cast<foo const&>(myFoo)[42] should also work as far as I can tell. Though, these kinds of casts are still a bit of a mystery to me. Cheers, SG |
Re: const correctness - should C++ prefer const member overnon-const?
On Oct 30, 11:41*am, blargg....@gishpuppy.com (blargg) wrote:
> I could have sworn "The Design and Evolution of C++" > covered the reason behind this, but I couldn't find a > reference. Maybe you mean section 3.7.1 ? -- <\___/> / O O \ \_____/ FTB. http://www.topaz3d.com/ - New 3D editor! |
Re: const correctness - should C++ prefer const member overnon-const?
On Oct 30, 11:45*am, blargg....@gishpuppy.com (blargg) wrote:
> As others have mentioned, a proxy object with an operator T () and > operator = ( T const& ) would be most transparent to the user. I don't see how that works for a struct... I want operator[] to return a reference to a struct and be able to do this: Foo f = myStuff[i].foo; and myStuff[i].foo = f; With the first one calling the const version of operator[]. -- <\___/> / O O \ \_____/ FTB. http://www.topaz3d.com/ - New 3D editor! |
| All times are GMT. The time now is 12:28 PM. |
Powered by vBulletin®. Copyright ©2000 - 2013, vBulletin Solutions, Inc.
SEO by vBSEO ©2010, Crawlability, Inc.