大家好,我是翼同学!
这篇笔记的内容是:在构造函数中使用new时的注意事项
我们知道,如果在类的构造函数里使用new
来初始化指针成员,则需要在析构函数里使用delete
来销毁掉。并且new
和delete
必须相互对于与兼容,也就是说new
对应于delete
,new[]
和delete[]
.
需要注意的是,如果有多个构造函数,则必须用相同的方法来使用new
语句。这是因为析构函数只有一个,构造函数里的new
语句必须和析构里的delete
语句相对应起来。
另外的,我们也可以在一个构造函数中使用new
初始化指针成员,然后在另一个构造函数中将指针成员初始化为空。这是由于析构函数中的delete
语句(无论带不带中括号[]
)都可以用于空指针。
比如说现在有一个简单String类,如下所示:
class String {
public:
String();
private:
int len;
string str;
};
下面举两个错误的构造函数。
代码如下:
String::String() {
str = "initialization";
len = std::strlen(str);
}
上面这个例子中并没有使用new
来初始化str
,而在析构函数里,对于不是new
初始化的指针使用delete
时,结果将是不确定,而且可能是有害的。
代码如下:
String::String(const char * ch) {
len = std::strlen(ch);
str = new char;
std::strcpy(str, ch);
}
例2的代码中确实用到了new关键字,但是问题出在内存量的分配。即new
返回的内存块只能保存一个字符,其无法将过长的字符串复制到new
出来的内存单元中,所以导致了内存问题。
以下三个代码块都是正确的构造函数示例:
String::String() {
str = 0;
len = 0;
}
或者是:
String::String() {
len = 0;
str = new char[1];
str[0] = '\0';
}
或者是:
String::String(const String & s) {
len = s.len;
str = new char[len+1];
std::strcpy(str, s.str);
}
好了,本篇笔记就到写这,欢迎大家到评论区一起讨论!
本章参考书:
《C++ Primer Plus》---- 史蒂芬·普拉达 著