在一个班级里
class Foo
{
public:
void DoSomething(int x) const;
private:
int m_bar;
};
不允许写
void Foo::DoSomething(int x) const
{
m_bar = x; // Error
}
我必须删除const
修饰符,但是,如果我有
struct Data
{
bar;
};
class Foo
{
public:
void DoSomething(int x) const;
private:
Data * m_data;
};
void Foo::DoSomething(int x) const
{
m_data->bar = x;
}
那么这不仅没问题,而且如果我删除修饰符,代码验证工具会警告我“方法可以是常量”?
我不应该在const方法中修改对象的状态,不管状态是如何表示的!
3条答案
按热度按时间x7yiwoj41#
const
限定符告诉编译器该函数不会修改对象的任何成员变量。因此,如果你有一个指针成员变量,const
函数将无法改变指针本身。***但***只适用于实际成员变量。指针实际指向的数据不是常量。为此,您需要一个指向常量对象的指针(例如
Data const* m_data;
)。nfzehxib2#
指针指向某处。如果你修改一个指针,你就修改了它指向的地方。
因为指针指向某个地方,所以可以取消引用它们来访问被指针。修改指针对象不会修改指针。
为了便于说明,假设你没有指针,而是有一个数组的索引:
当然指针不是数组的索引。虽然作为心理图像,它比你想象的更准确。索引引用存储在别处的实际对象。可以修改对对象没有影响的索引。您可以使用索引访问对象并修改它,而无需修改索引。这和你的指针是一样的。
我希望现在很明显
Foo::DoSomething
应该是const
。您正在修改Data
对象,该对象不是Foo
的一部分。Foo
只包含指向对象的指针。DoSomething
不会修改该指针。mcvgt66p3#
对象在某个地址P占用某个X内存。带有
const
限定符的成员函数不能DIRECTLY更改此地址的内存X,这就是为什么函数可以标记为const
在下面的例子中,我们CAN改变
const
对象中对象的内存编译并运行:
将得到: