二叉树重建(前序遍历+中序遍历+不能重复)

主要是确定左子树的区间和右子树的区间,然后递归的进行,首先根据前序遍历的根节点(一定在区间的第一个位置)在中序遍历中找到对应的位置,就可以确定左子树的长度,从而就可以确定前序遍历的左子树以及右子树以及中序遍历的左子树和右子树

struct TreeNode{
	char val;
	TreeNode(){ val = 0; left = nullptr; right = nullptr; }
	TreeNode(char n) :val(n), left(nullptr), right(nullptr){}
	TreeNode* left;
	TreeNode* right;

};

TreeNode* buildtree(string& preorder,int pl,int pr, string& inorder,int il,int ir){
	if (preorder.empty() || inorder.empty()){
		if (preorder.empty() && !inorder.empty())
			cout << "error input";
		if (!preorder.empty() && !inorder.empty())
			cout << "error input";
		return nullptr;
	}
	if ((pl > pr) || (il > ir)){
		return nullptr;
	}
	int length1 = pr - pl+1;
	int length2 = ir - il+1;
	if (length1 != length2){
		cout << "error input";
		return nullptr;
	}
	TreeNode* root = new TreeNode(preorder[pl]);
	int i = il;
	while (i<=ir&&inorder[i] != root->val)i++;
	if (i > ir){
		cout << "error input";
		return nullptr;
	}
	
	TreeNode* left = buildtree(preorder, pl + 1, pl + i - il, inorder, il, i - 1);
	TreeNode* right = buildtree(preorder, pl + i - il + 1, pr, inorder, i + 1, ir);
	root->left = left;
	root->right = right;
}
void printtree_preorder(TreeNode* root){
	if (root == nullptr)return;
	
	cout << root->val;
	printtree_preorder(root->left);
	printtree_preorder(root->right);
}
void printtree_inorder(TreeNode* root){
	if (root == nullptr)return;
	
	
	printtree_inorder(root->left);
	cout << root->val;
	printtree_inorder(root->right);
}
void delete_tree(TreeNode* root){
	if (root == nullptr)return;
	delete_tree(root->left);
	delete_tree(root->right);
	delete(root);
}
int main(){
	string preorder = "ABCDEFGHI";
	string inorder = "BCAEDGHFI";
	TreeNode* root=buildtree(preorder,0,preorder.size()-1,inorder,0,inorder.size()-1);
	printtree_preorder(root);
	cout << endl;
	printtree_inorder(root);
	delete_tree(root);
	return 0;
}

 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值