const、volatile、mutable关键字
const關(guān)鍵字
變量宏方面:
const 修飾變量:常量非指針類型,非指針常量類型并沒有什么區(qū)別。
const修飾指針:常量指針:是指針不過指向的是常量可以進(jìn)行p++操作不能進(jìn)行*p操作;指針常量:是常量,不過有一個(gè)指向它地址的指針,可以進(jìn)行*p操作,不可以進(jìn)行p++操作。
用常量代替宏的作用,讓代碼更加易于調(diào)試。
函數(shù)方面:
常量函數(shù)參數(shù),可以簡化代碼和允許常量傳入函數(shù),因?yàn)樽兞靠梢再x值給常量,但是常量不能賦值給變量。
函數(shù)常量返回值,避免返回值間相互賦值,改變返回值。
類對象方面:
常量對象,常量引用,說明常量和引用是不可以改變的。
常量數(shù)據(jù)成員,才構(gòu)造函數(shù)初始化列表中給出,保護(hù)數(shù)據(jù)作用,數(shù)據(jù)不能改變。
常量成員函數(shù),是函數(shù)不能修改類數(shù)據(jù)成員的(如果有mutable修飾的數(shù)據(jù)成員還是可以修改的)。
volatile關(guān)鍵字
volatile的本意是“易變的”,volatile關(guān)鍵字是一種類型修飾符,用它聲明的類型變量表示可以被某些編譯器未知的因素更改,比如操作系統(tǒng)、硬件或者其它線程等。遇到這個(gè)關(guān)鍵字聲明的變量,編譯器對訪問該變量的代碼就不再進(jìn)行優(yōu)化,從而可以提供對特殊地址的穩(wěn)定訪問。
當(dāng)要求使用volatile?聲明的變量的值的時(shí)候,系統(tǒng)總是重新從它所在的內(nèi)存讀取數(shù)據(jù),即使它前面的指令剛剛從該處讀取過數(shù)據(jù)。而且讀取的數(shù)據(jù)立刻被寄存。例如:
volatile int i=10;
int a = i;
。。。//其他代碼,并未明確告訴編譯器,對i進(jìn)行過操作
int b = i;
volatile?指出?i是隨時(shí)可能發(fā)生變化的,每次使用它的時(shí)候必須從i的地址中讀取,因而編譯器生成的匯編代碼會重新從i的地址讀取數(shù)據(jù)放在b中。而優(yōu)化做法是,由于編譯器發(fā)現(xiàn)兩次從i讀數(shù)據(jù)的代碼之間的代碼沒有對i進(jìn)行過操作,它會自動(dòng)把上次讀的數(shù)據(jù)放在b中。而不是重新從i里面讀(如果是用volatile修飾了那么就會從i中重新讀取變量)。這樣以來,如果i是一個(gè)寄存器變量或者表示一個(gè)端口數(shù)據(jù)就容易出錯(cuò),所以說volatile可以保證對特殊地址的穩(wěn)定訪問。
mutable關(guān)鍵字
mutalbe的中文意思是“可變的,易變的”,跟constant(既C++中的const)是反義詞。在C++中,mutable也是為了突破const的限制而設(shè)置的。被mutable修飾的變量(mutable只能由于修飾類的非靜態(tài)數(shù)據(jù)成員),將永遠(yuǎn)處于可變的狀態(tài),即使在一個(gè)const函數(shù)中。
我們知道,假如類的成員函數(shù)不會改變對象的狀態(tài),那么這個(gè)成員函數(shù)一般會聲明為const。但是,有些時(shí)候,我們需要在const的函數(shù)里面修改一些跟類狀態(tài)無關(guān)的數(shù)據(jù)成員,那么這個(gè)數(shù)據(jù)成員就應(yīng)該被mutalbe來修飾。下面是一個(gè)小例子:
class ClxTest
{
public:
void Output() const;
};
?
void ClxTest::Output() const
{
cout << "Output for test!" << endl;
}
?
void OutputTest(const ClxTest& lx)
{
lx.Output();
}
類ClxTest的成員函數(shù)Output是用來輸出的,不會修改類的狀態(tài),所以被聲明為const。
函數(shù)OutputTest也是用來輸出的,里面調(diào)用了對象lx的Output輸出方法,為了防止在函數(shù)中調(diào)用成員函數(shù)修改任何成員變量,所以參數(shù)也被const修飾。
假如現(xiàn)在,我們要增添一個(gè)功能:計(jì)算每個(gè)對象的輸出次數(shù)。假如用來計(jì)數(shù)的變量是普通的變量的話,那么在const成員函數(shù)Output里面是不能修改該變量的值的;而該變量跟對象的狀態(tài)無關(guān),所以應(yīng)該為了修改該變量而去掉Output的const屬性。這個(gè)時(shí)候,就該我們的mutable出場了,只要用mutalbe來修飾這個(gè)變量,所有問題就迎刃而解了。下面是修改過的代碼:
class ClxTest
{
public:
ClxTest();
~ClxTest();
?
void Output() const;
int GetOutputTimes() const;
?
private:
mutable?int m_iTimes;
};
?
ClxTest::ClxTest()
{
m_iTimes = 0;
}
?
ClxTest::~ClxTest()
{}
?
void ClxTest::Output() const
{
cout << "Output for test!" << endl;
m_iTimes++;
}
?
int ClxTest::GetOutputTimes() const
{
return m_iTimes;
}
?
void OutputTest(const ClxTest& lx)
{
cout << lx.GetOutputTimes() << endl;
lx.Output();
cout << lx.GetOutputTimes() << endl;
}
計(jì)數(shù)器m_iTimes被mutable修飾,那么它就可以突破const的限制,在被const修飾的函數(shù)里面也能被修改。
總結(jié)
以上是生活随笔為你收集整理的const、volatile、mutable关键字的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: bzoj1025题解
- 下一篇: 使用foreach循环遍历集合元素