类中fstream引用成员在const函数调用非const的seekg为何能编译?
为什么const成员函数里能调用fstream&的非const成员函数?
这是个很有意思的问题,核心在于C++中const成员函数对引用类型成员变量的处理逻辑和普通成员变量不一样。
先把你的代码贴出来方便对照:
class Test { fstream &f; public: Test(fstream &f_): f(f_) {} int fid() const { f.seekg(5); return 0; } };
我们先回忆下const成员函数的基本规则:在const成员函数内部,所有非静态成员变量都会被视为const限定的版本——但这个规则对引用类型的成员有特殊处理:
- 如果是普通成员变量(比如
fstream f;),在const函数里它会变成const fstream f;,这时候调用非const的seekg肯定会编译报错,因为const对象只能调用const成员函数。 - 但你的成员是引用类型
fstream& f:在const成员函数中,引用本身的“绑定关系”是不能被修改的(引用从一开始就不能被重新绑定,const函数只是强化了这一点),但引用指向的对象本身并不会被加上const限定。也就是说,在fid()这个const函数里,f仍然是一个指向非const fstream对象的引用,自然可以调用它的非const成员函数seekg。
简单来说:const成员函数只会阻止你修改成员变量本身,但对于引用成员,“修改成员变量本身”指的是改变引用的绑定对象(而这本来就做不到),但不会限制你通过引用修改指向的对象。
如果你想让这个const函数无法调用seekg,可以把成员变量改成const fstream& f——不过这样的话你本来就不能调用非const成员函数了,这显然不是你想要的。
总结一下:引用成员在const函数里,其指向的对象仍然保持原有的非const属性,所以你能调用它的非const成员函数,这完全符合C++的规则。
内容的提问来源于stack exchange,提问作者forumulator
相关产品推荐
相关产品推荐

