C++常數成員函數

2020-07-16 10:04:41
通過參照或通過指標傳遞給函數的形參可能會被該函數修改。但是如果在形參中使用 const 關鍵字,則可以防止呼叫的函數修改它。

例如,某個函數的宣告如下:

void fun (const string &str);

該函數釆用了一個字串物件的參照作為形參,但不能修改該物件。有一個類似的機制,可以用來保護隱含的形參 *this,使它不會被成員函數修改。當定義成員函數時,可以在形參列表後面放置 const 關鍵字,這實際上就是告訴編譯器,該成員函數未被允許修改其物件。如果成員函數定義在類外面,則類內的宣告和類外的定義都必須具有 const,範例如下:
class ConstExample
{
    int x;
    public:
        ConstExample(int a){ x = a;}
        void setValue(int);
        int getValue() const;
};
getValue 函數定義語句應如下:
int ConstExample::getValue() const
{
    return x;
}
具有常數形參 X 的函數無法轉向,並將 X 作為非常數形參傳遞給另一個函數。換句話說,承諾不修改 X 的函數不能將X傳遞給另一個函數,除非第二個函數也承諾不修改 X。這種情況有時也可能會以不明顯的方式發生。

以下程式使用帶有常數形參的函數來列印陣列的第一個元素,但是它不會編譯,因為它在 const 的使用方面不一致:
#include <iostream>
using namespace std;

class K
{
    public:
        void output () // 丟矢了 const
        {
            cout << "Output of a K object" << endl;
        }
};
void outputFirst(const K arr[])
{
    arr[0] .output ();
}
int main(int argc, char** argv)
{
    K arr [] = { K() };
    outputFirst(arr);
    return 0;
}
該程式之所以不能編譯,是因為編譯器不能保證 const 陣列的元素在作為隱含的 this 形參傳遞給 output 成員函數時不會被修改:

arr[0].output();

要讓該程式可以編譯,則可以使 output() 成員函數變成一個 const 成員函數,以表示它有一個作為常數的 this 形參,範例如下:
class K
{
    public:
        void output() const
        {
            cout << "Output of a K object" << endl;
        }
};