二叉树非递归前、中、后序遍历实现

struct node
{
	char data;
	struct node *left;
	struct node *right;
	bool print; //是否打印值,右子树遍历完需要打印,左子树处理完不需要,后序遍历需要 
};

/*非递归先序遍历*/
void first_scan(struct node *tree){
	if (!tree){
		return;
	}
	stack<struct node *> sta;

	//迭代
	while(tree){ //直到所有要处理的树处理完
		putchar(tree->data);
		if (tree->left){ //左子树非空
			sta.push(tree); //遍历右子树还需要用到
			tree = tree->left; //左子树为当前要处理的树
		}else if (tree->right){ //右子树非空
			tree = tree->right; //右子树为当前要处理的树
		}else{ //左右子树都为空
			bool find = false; //是否有找到新的要处理的树
			while(!sta.empty()){
				tree = sta.top(); //出栈
				sta.pop();
				if (tree->right){ //右子树非空
					tree = tree->right; //右子树变为当前要处理的树
					find = true;
					break;
				}
			}
			if (!find){
				tree = NULL; //没有要处理的树了
			}
		}
	}
	putchar('\n');
}


/*非递归中序遍历*/
void medium_scan(struct node *tree){
	if (!tree){
		return;
	}
	stack<struct node *> sta;

	while(tree){ //直到所有要处理的树处理完
		if (tree->left){ //左子树非空
			sta.push(tree); //便于左子树处理完后再处理
			tree = tree->left; //左子树为当前要处理的树
		}else{ //左子树为空
			putchar(tree->data); //打印当前值
			if (tree->right){ //右子树非空
				tree = tree->right; //右子树为当前要处理的树
			}else{ //右子树为空,当前树已处理完
				bool find = false; //是否有找到新的要处理的树
				while(!sta.empty()){ 
					tree = sta.top(); //出栈
					sta.pop();
					putchar(tree->data); //左子树已处理完,打印当前值
					if (tree->right){ //右子树非空
						tree = tree->right; //右子树为当前要处理的树
						find = true;
						break;
					}
				}
				if (!find){
					tree = NULL; //没有要处理的树了
				}
			}
		}
	}
	putchar('\n');
}

/*非递归后序遍历*/
void last_scan(struct node *tree){
	if (!tree){
		return;
	}
	stack<struct node *> sta;

	while(tree){
		if (tree->left){//左子树非空
			tree->print=false;//左子树处理完后根节点不需要打印
			sta.push(tree);//便于后续遍历右子树
			tree=tree->left;//左子树为新的当前要处理的树
		}else if(tree->right){//右子树非空
			tree->print=true;//右子树遍历完后需要打印根节点值
			sta.push(tree);//便于右子树遍历完后打印当前树根节点
			tree=tree->right;//右子树为当前要处理的树
		}else{//左、右子树都为空
			putchar(tree->data);//左右子树都为空,打印根节点值,结束当前树的处理
			bool find = false;//是否有找到新的要处理的树
			while(!sta.empty()){
				tree=sta.top();
				sta.pop();
				if(!tree->print){//左子树遍历完,不需要打印根节点
					if(tree->right){//右子树非空
						tree->print=true;//右子树遍历完需要打印根节点值
						sta.push(tree);//便于右子树遍历完后打印根节点值
						tree=tree->right;//右子树为当前要处理的树
						find=true;
						break;
					}else{//右子树为空,打印根节点值,结束当前树的处理
						putchar(tree->data);
					}
				}else{//右子树遍历完
					putchar(tree->data);//左右子树都遍历完,打印根节点结束当前树的处理
				}
			}
			if(!find){//没有要处理的树了
				tree=NULL;
			}
		}
	}
	putchar('\n');
}


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值