给出以下代码:
template <class T>
class A {
T* arr;
int size;
public:
A(int size) : arr(new T[size]) , size(size) {
}
//..
A& operator=(const A& a){
if(this == &a){
return *this;
}
this->size = a.size;
T* ar=new T[a.size];
for(int i=0 ; i<size ; i++){
ar[i]=a.arr[i]; // I need to do it at "try-catch" ?
}
delete[] this->arr;
this->arr=ar;
return *this;
}
//...
};
当我从给定数组中复制元素时,是否需要使用try-catch
子句来完成?这是个好主意吗?
答案 0 :(得分:0)
我发现您的T副本可能由于其自身的分配失败或其他原因而抛出。
另一方面,您的A副本可能已经抛出,因为它的分配失败。
当前,您将需要处理销毁,因为您尚未具体化已分配的阵列,并且如果其中一个异常(可能是由于分配失败)而导致的,则已创建的所有T实例都需要销毁。
一种快速解决此问题的方法是将数组保留在unique_ptr中。然后它将在退出上下文时销毁。
另一种方法可能是在分配异常后重新考虑您在A上的合同:该合同必须有效,即可以继续使用,但是可能不必保证仍包含其先前的内容或所有新的内容,因此您可以在分配和分配新数组之前决定销毁其现有数组,然后复制成员。如果大小没有更改,您可以决定不重新分配,而只是重新分配-这会在出现异常后留下一堆新成员和旧成员,但是它们都是有效且可以安全删除的。
请确保大小始终与实际连接的阵列大小匹配!您现有的代码会犯此错误,但特别是在删除后和赋值之前将其设置为null和0。并且仅在分配新指针后才将其设置为新的新大小。