我对C++中的可变变量有以下理解。
- 这是一个特殊的存储类
- 可变变量可以由常量对象修改
- 想要使用可变变量的一个例子是,除非特别要求,否则不想执行昂贵的操作来获得结果。如果有特殊要求,您的程序将执行一次操作,并将结果缓存在可变变量中
我的问题是关于记忆力。编译器将可变变量存储在内存中的何处?既然它是可修改的,那么它肯定不会是"只读"存储器。
mutable
(可变(只是编译器(如const
或volatile
(的类型限定符。类的成员存储在一个连续的内存块上(静态的除外(。如果将成员定义为const
,并不意味着编译器会将其放置在RO内存中。const
声明在运行时不会产生任何影响,它只是编译器在编译期间执行适当检查和优化的关键字。一旦您将一个类(或方法(定义为const
,但仍需要修改该类的特定成员(如互斥对象或您提到的缓存值(,您就可以让编译器知道该特定成员是mutable
,否则将出现编译错误。
这可能是编译器特定的,但我想大多数编译器只会选择始终将具有可变成员的类(整个类(定位到非常量内存中,以实现这一点。
这完全取决于编译器,它可以执行转义分析并确定对象永远不能被修改,在这种情况下,它可以被写入二进制文件的read-only
部分。mutable
存储类说明符只放宽了编译时的要求。
不过,对象需要按声明顺序分配,因此无论存储类说明符如何,所有变量都在同一内存区域中。但是,如果机器支持const
字节区域,则没有什么可以阻止在该区域设置read-only
位。
类的所有成员的大小(由sizeof
确定(至少为1
。对于mutable
成员也是如此,这意味着所有类成员都必须在内存中占据一定范围的位置。
mutable
成员唯一的特殊之处在于,它的值可以更改,即使它在const
对象中也是如此。这取决于编译器如何实现。通常,编译器在编译时强制执行常量。换句话说,如果一个对象是const
,其成员在逻辑上也是const
,并且试图对任何成员进行修改(或调用非const
操作(,则除非该成员是mutable
,否则代码将不会编译。
实际上,不需要在运行时将const
对象或其成员弹出到只读内存中。如果真的做到了,那么就需要进行一些特殊处理,以允许其mutable
成员进行更改,即使阻止了对其他成员的更改。例如,对象的所有成员都可能被放置在可修改的内存中,只有不可变的成员被标记(例如,使用操作系统支持(,因此它们在运行时无法更改。
使用可变成员的一个常见原因是存储可重复的昂贵操作的结果(对于相同的输入给出相同的结果(。如果不需要结果,也不需要昂贵的操作。如果需要重复访问结果,那么可变成员允许第一次存储结果,而不是重复执行昂贵的操作。