所以我对C ++中的拷贝构造函数感到很困惑。我有以下代码:
class creature /* abstract class*/
{
private:
string name;
int longevity;
creature_society * cs;
public:
creature(int,int,int,creature_society*);
//creature(const creature&);
virtual ~creature();
virtual int is_a_good() =0;
};
class good_creature : public creature
{
public:
good_creature(int,int,creature_society*);
//good_creature(const good_creature&);
~good_creature();
int is_a_good() //returns 1
};
class bad_creature : public creature
{
public:
bad_creature(int,int,creature_society*);
//bad_creature(const bad_creature&);
~bad_creature();
int is_a_good(void); //returns 0
}
所以我有一个名为 creature
的抽象类,一个 good_creature
和一个 bad_creature
,它们是 creature
的子类。
在我的程序中,我还有一个名为society
的数组,其类型为creature*
个对象。如果通过条件将我的生物定义为好,我会为其分配空间并将其作为society
存储在good_creature
数组中。坏生物也是如此。我按照以下代码中的描述构建它:
society = new creature*[M];
for(i=0;i<M;i++)
{
if(condition)
society[i] = new good_creature(L,good,this);
else
society[i] = new bad_creature(L,bad,this);
}
所以我必须创建一个纯虚函数:creature::clone(int position)
如果它是good_creature
或bad_creature
,它必须删除society[pos]
并制作副本society[pos-1]
通过复制构造函数。
例如,我的good_creature::clone(int position)
就像这样:
void good_creature::clone(int position)
{
int cop_pos=position -1; //getting the position before that in order to copy it
delete society[pos];
society[pos] = new good_creature( *society[cop_pos] );
//....
}
我收到错误,因为society[cop_pos]
的类型为creature*
。我尝试将它投射到好的生物上,但遗憾的是我一直在犯错误。是因为我没有正确地调用复制构造函数,是不是因为我不正确?有任何想法吗?这已经让我喘不过气来2天了。请记住,我是一个新手,可能做错了。
此外,我不需要定义自己的复制构造函数,因为society[i]
中的所有元素都指向由creature_society * cs
定义的同一对象,因此我尝试使用默认构造函数因为我不需要深层复制。
感谢您的时间。
更新
我忘了提及的课程和我建立社会的方式
class creature_society
{
private:
int N; // number of the creatures we want to be made in society
creature ** society;
public:
creature_society(int,int);
~creature_society();
};
答案 0 :(得分:4)
你不知道society[cop_pos]
是否是正确的类型,所以你不能安全地施放。更好的解决方案是使用虚函数创建副本
class creature {
public:
virtual creature* clone() const = 0;
...
};
class good_creature {
public:
good_creature* clone() { return new good_creature(*this); }
...
};
//Similar for bad_creature (and any other derived classes)
在您的情况下,您可以这样称呼它:
society[pos] = society[cur_pos]->clone();
无需知道您要克隆的对象的类型。虚函数调用会为您处理。请注意,good_creature::clone
会返回good_creature*
而不是creature*
。这是一个有效的过载。允许虚函数重载返回派生类。在这种情况下,您可以让它返回creature*
。
答案 1 :(得分:3)
使用多态和虚拟调度为您完成工作。
在生物类中定义克隆虚拟函数。
class creature
{
virtual creature * clone() = 0;
}
然后在子项中覆盖它:
class good_creature: public creature
{
virtual creature * clone() override
{
return new good_creature(*this);
}
}
和bad_creature类似。
然后使用它:
society[pos] = society[pos - 1]->clone();
旁注:您的设计似乎受到Java等语言的影响。这不是(现代)C ++风格。例如,在现代C ++中,所有权更好地由unique_ptr
表示,而不是指针。这将使代码更清晰,更安全。
答案 2 :(得分:1)
问题是society
是creature
的数组,而不是good creature
,因此复制构造函数不适用。
您可以为good_creature
和bad_creature
定义构造函数作为生物的参数:
good_creature(const creature&);