[英]Passing by reference to a constructor
我決定查看是否為成員分配引用會使成員成為引用。 我編寫了以下代碼片段來測試它。 有一個簡單的類Wrapper
,其中std::string
作為成員變量。 我在構造const string&
取一個const string&
並將其分配給public成員變量。 后來在main()
方法中我修改了成員變量但是我傳遞給構造函數的string
保持不變,怎么樣? 我認為在Java中變量會發生變化,為什么不在這段代碼中呢? 在這種情況下,引用究竟是如何工作的?
#include <iostream>
#include <string>
using namespace std;
class Wrapper
{
public:
string str;
Wrapper(const string& newStr)
{
str = newStr;
}
};
int main (int argc, char * const argv[])
{
string str = "hello";
cout << str << endl;
Wrapper wrapper(str);
wrapper.str[0] = 'j'; // should change 'hello' to 'jello'
cout << str << endl;
}
要在構造函數中指定引用,您需要具有引用成員
class A{
std::string& str;
public:
A(std::string& str_)
: str(str_) {}
};
str現在是對傳入的值的引用。同樣適用於const引用
class A{
const std::string& str;
public:
A(const std::string& str_)
: str(str_) {}
};
但是不要忘記,一旦分配了引用,它就無法更改,因此如果賦值需要更改為str,那么它必須是指針。
因為Wrapper::str
不是引用,所以它是一個獨立的對象。 所以當你執行str = newStr
,你正在復制字符串。
class Wrapper
{
public:
string& str;
Wrapper(string& newStr) : str(newStr) {}
};
注意,你不能接受一個const string&
並將它存儲在一個string&
,這樣做會失去const-correctness。
您需要使用初始化程序並將str
聲明為引用,如下所示:
class Wrapper {
public:
string &str;
Wrapper(string& newStr)
: str(newStr) {
}
};
你編寫它的方式,你所做的就是復制傳遞給構造函數的引用的值。 你沒有保存參考。 通過將引用聲明為類成員並使用對另一個字符串實例的引用對其進行初始化,您將獲得您正在尋找的行為。
你的主體變量是std::string
。
你的參數變量是const std::string&
。
引用中的const始終是“低級別const”,這意味着它修改了對象的類型而不是實際對象。
相比之下,“頂級const”修改了一個實際的對象。 閱讀頂級const上的C ++ Primer以獲得澄清。
傳遞參數時,您的任務如下所示:
const std::string& = std::str; //Values are ommited
// i.e const std::string newStr = std::string str
您正在使用可接受的non-const value
初始化const type reference
。 您不應該使用該引用更改std::string str
的值。 並且,如果您嘗試在構造函數中更改newStr
的值,您將收到編譯錯誤 。
接下來,你在構造函數中做了另一個賦值,這也是可以接受的:
std::string = const std::string
這一事實wrap.str[0]
不改變str
的main
是,雖然參考了用於實例化class str
, class str
有它自己的對象和未鏈接到main str
。 在參數中使用該引用只是將該參數鏈接到main str
; 不是main str
class str
。
如果引用了類變量,那么它可能已經改變了。
您應該將Wrapper::str
聲明為string&
而不是string
。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.