我正在学习C ++作为一种爱好,并且正在努力使用“new”来动态创建一个类对象。我已经读过动态创建的类不会丢失范围,但这似乎不适用于我的简单示例。
执行时,'testValue1'的值在构造函数中设置为555并打印。当控件返回main时,'testvalue'很遗憾地设置为0(或未定义 - 不确定)。我可以在main中设置值,并在main和for循环中正确维护该值。
问题:我不明白为什么当控制返回到main时,不保持初始值555。我知道我做错了什么或者没有正确理解动态分配的类对象的范围......任何帮助都表示赞赏。以下是示例代码:
//main.cpp
#include <iostream>
using namespace std;
class generalVars
{
private:
public:
//data attributes
int testValue1;
//constructor
generalVars()
{
cout << "I am in general vars constructor" << endl;
int testValue1= 555;
cout << "testValue1 has been set " << testValue1 << endl;
}
~generalVars(void)
{
cout << "I am in general vars destructor" << endl;
};
};
int main(int argc, char *argv[])
{
cout << "I am in Main" << endl;
generalVars* myGeneralVars = new generalVars; //create on heap
cout << "Main1 testvalue1 = " << myGeneralVars->testValue1 << endl;
myGeneralVars->testValue1 = 777;
cout << "Main2 testvalue1 = " << myGeneralVars->testValue1 << endl;
for (int i=0; i<= 3; i++)
{
cout << "Inside while loop..." << endl;
cout << "Main3 " << i << " testvalue1 = " << myGeneralVars->testValue1 << endl;
}
delete myGeneralVars; //delete from heap
return 0;
}
答案 0 :(得分:4)
本声明:
int testValue1= 555;
声明本地变量,与同名的数据成员不同。
所以它不会改变成员的价值。
相反,例如。
testValue1= 555;
或者使用构造函数的内存初始化列表,如下所示:
generalVars()
: testValue1( 555 )
{
cout << "I am in general vars constructor" << endl;
cout << "testValue1 has been set " << testValue1 << endl;
}
答案 1 :(得分:2)
正在发生两件事:
1)通过将int放在前面来重新声明testValue1:
generalVars()
{
cout << "I am in general vars constructor" << endl;
int testValue1= 555; //right here!
cout << "testValue1 has been set " << testValue1 << endl;
}
这将使用同名的新唯一变量隐藏类自己的testValue1实例。您可以像这样引用它们:
generalVars()
{
cout << "I am in general vars constructor" << endl;
int testValue1= 555; //note, still has int
cout << "testValue1 has been set " << testValue1 << endl;
cout << "this->testValue1 has not been set and is " << this->testValue1 << endl;
this->testValue1 = 555; //note, this->
cout << "this->testValue1 has been set " << this->testValue1<< endl;
}
或者您可以避免名称冲突并正常引用它:
generalVars()
{
cout << "I am in general vars constructor" << endl;
testValue1= 555; //note, no int. This is identical to this->testValue1
cout << "testValue1 has been set " << testValue1 << endl;
}
接下来不是一个真正的问题,但应该注意:
在大多数情况下,您不需要使用C ++中的new分配内容。您应该更喜欢堆栈分配的对象
generalVars myObject;
而不是:
generalVars *myObject = new generalVars();
...
delete myObject;
或者,如果您确实想要创建堆分配对象:
auto myObject = std::make_unique<generalVars>();
或者,如果您需要多个句柄:
auto myObject = std::make_shared<generalVars>();
unique_ptr和shared_ptr示例不需要显式删除。当指针对象超出范围时,将删除堆分配。这特别有助于异常安全。
答案 2 :(得分:2)
您在generalVars构造函数中定义了另一个变量,并将init值定义为555,对于init成员testValue1,您不需要在构造函数中再次定义它。
更新
generalVars()
{
cout << "I am in general vars constructor" << endl;
int testValue1= 555; // this defines another testValue1 variable. it's different from member testValue1
cout << "testValue1 has been set " << testValue1 << endl;
}
到
generalVars()
{
cout << "I am in general vars constructor" << endl;
testValue1= 555; // Note, removed int
cout << "testValue1 has been set " << testValue1 << endl;
}