复制构造函数和析构函数八叉树C++
我已经创建了一个八叉树数据结构,但它并不完美。我正在努力与复制构造函数和析构函数。 这里是我的头文件:复制构造函数和析构函数八叉树C++
class Octree
{
public:
static int lastbranch;
static bool utolsoelotti;
struct node
{
int value;
node *child[8];
};
Octree();
~Octree();
Octree(const Octree& oct);
void clear(node* node);
node* searchandset(int dec, int value);
node* search(int dec);
node* step(node *node, int k);
node* copy(node *n);
void Print(node *n)const;
void deletebranch(int branch);
node *root;
};
构造函数,析构函数,复制contrsuctor
Octree::Octree()
{
root = new node;
root->value = 0;
for (int i = 0; i < 8; i++)
root->child[i] = 0;
}
Octree::~Octree()
{
clear(root);
}
Octree::Octree(const Octree& oct) {
root = copy(oct.root);
}
void Octree::clear(node *node){
for (int i = 0; i < 8; i++)
if (node->child[i])
clear(node->child[i]);
delete node;
}
Octree::node*Octree::copy(node *n) {
node* n2 = new node;
if (n) {
for (int i = 0; i < 8; i++) {
n2->child[i] = copy(n->child[i]);
}
}
return n2;
}
这里是我创建的主要对象:
int main() {
Octree tree;
Octree tree2(tree);
tree.searchandset(8, 2);
tree2.Print(tree2.search(8));
return 0;
}
在searchandset
功能我给第一棵树上的节点编号8给出一个值。之后,我调用复制构造函数并打印第二棵树的第8个节点。这个值与我给第一棵树的值相同,但是当被称为我的引诱者总是得到这个异常:
异常抛出:读取访问冲突。 节点是0xDDDDDDDD。
据我所知,这意味着我试图删除我已经删除的节点。对象'tree2'是与'tree'不同的对象,具有相同的值和节点不是它吗?然后我不明白上面的例外。 我是C++的新手,我知道它是基本的东西,所以如果有人会指引我进入正确的方向,我将非常感激。
问题出在copy
函数。让我们也通过一步一步:
node* n2 = new node;
if (n) {
for (int i = 0; i < 8; i++)
n2->child[i] = copy(n->child[i]);
}
return n2;
对于空Octree oct
,默认构造函数构建,并复制到另一个Octree
:
- 创建一个新的
node
,n2
-
n
是因此true
-
child[i]
的n2
有相应子的copy
的价值,因此再次呼吁copy
- 新节点
n2
创建 -
n
是nullptr
(因为其中oct
所有nullptr
的孩子),所以不执行条件 - 返回
n2
- 重复步骤
3
到6
8倍 - 返回根
n2
- 分配新指针(
n2
)来复制的对象
但是,root
等待!您是否注意到在步骤6中,您是return
一个新的指针,即使该孩子应该是nullptr
!
这就是问题所在,因为在clear
中,你会遍历每个孩子。这还行,对吧?但是,您尝试访问未初始化的子项(它们具有随机值,条件将评估为true
),因此您获得Read access violation
,因为这不是你的记忆。
那么解决方案?如果n
不是nullptr
,则仅分配内存n2
。
我上面编辑了我的代码。这就是你想要的吗?如果我这样做没有“读取访问冲突”,但复制树的值与原始树的值不同。 –
@ T.dog是的,因为您没有复制该值 – Rakete1111
@ T.dog不要更新问题中的原始代码。 – 0x499602D2
不应该'copy'返回'n2'? – Rakete1111
你说得对。但问题仍然存在。 –
如果你复制一个有空子节点的节点,那么在副本中,空子节点在原来的对应槽中的节点内容是什么? – HostileFork