代码随想录算法训练营第十四天| 二叉树的前序、中序、后序遍历

今日力扣题目链接:

前序遍历

后序遍历

中序遍历

二叉树的递归遍历

好像也没什么好说的,搞懂原理之后还是比较简单的。

前序——中左右

class Solution {
public:
	void preTra(TreeNode* cur, vector<int>& result) {
		if (cur == nullptr) return;
		else {
			result.push_back(cur->val);
			preTra(cur->left, result);
			preTra(cur->right, result);
		}
	}
	vector<int> preorderTraversal(TreeNode* root) {
		vector<int> result;
		preTra(root, result);
		return result;
	}
};

后序——左右中

class Solution {
public:
	void posTra(TreeNode* cur, vector<int>& result) {
		if (cur == nullptr) return;
		else {
			posTra(cur->left, result);
            posTra(cur->right, result);
            result.push_back(cur->val);
		}
	}
    vector<int> postorderTraversal(TreeNode* root) {
        vector<int> result;
		posTra(root, result);
		return result;
    }
};

中序——左中右

class Solution {
public:
    void inoTra(TreeNode* cur, vector<int>& result) {
	    if (cur == nullptr) return;
	    else {
	        inoTra(cur->left, result);
            result.push_back(cur->val);
            inoTra(cur->right, result);
	    }
    }
    vector<int> inorderTraversal(TreeNode* root) {
        vector<int> result;
		inoTra(root, result);
		return result;
    }
};

二叉树的迭代遍历

在迭代遍历中,前序、后序遍历和中序遍历有所不同。

前序遍历因为是中左右的顺序,需要在遍历完一个根节点之后再放入两个子节点。

class Solution {
public:
	vector<int> preorderTraversal(TreeNode* root) {
		if (root == nullptr) return vector<int> {};
		vector<int> result;
		stack<TreeNode*> stk;
		stk.push(root);
		while (!stk.empty()) {
			result.push_back(stk.top()->val);
			TreeNode* tmp = stk.top();
			stk.pop();
			if (tmp->right) stk.push(tmp->right);
			if (tmp->left) stk.push(tmp->left);
		}
		return result;
	}
};

后序遍历是右左中的顺序,只要翻转一下就是中右左,和前序遍历很像,改改形式就行。

class Solution {
public:
	vector<int> postorderTraversal(TreeNode* root) {
		if (root == nullptr) return vector<int> {};
		vector<int> result;
		stack<TreeNode*> stk;
		stk.push(root);
		while (!stk.empty()) {
			result.push_back(stk.top()->val);
			TreeNode* tmp = stk.top();
			stk.pop();
			if (tmp->left) stk.push(tmp->left);
			if (tmp->right) stk.push(tmp->right);
		}
		reverse(result.begin(), result.end());
		return result;
	}
};

 而中序遍历却不同,因为中序遍历是左中右的顺序,在遇到根节点的时候需要先判断其有没有左节点,如果有左节点要先将左节点加入栈遍历,然后遍历根节点,最后再找有没有右节点。

class Solution {
public:
	vector<int> inorderTraversal(TreeNode* root) {
		if (root == nullptr) return vector<int> {};
		vector<int> result;
		stack<TreeNode*> stk;
		TreeNode* cur = root;
		while (cur || !stk.empty()) {
			if (cur) {
				stk.push(cur);
				cur = cur->left;
			}
			else {
				cur = stk.top();
				result.push_back(cur->val);
				stk.pop();
				cur = cur->right;
			}

		}
		return result;
	}
};

二叉树的统一迭代法

统一迭代法是在根节点之后添加一个空指针用于表明该节点是根节点,从而实现三种遍历有相同的遍历格式。

前序遍历

class Solution {
public:
	vector<int> preorderTraversal(TreeNode* root) {
		if (!root) return vector<int> {};
		vector<int> result;
		stack<TreeNode*> stk;
		TreeNode* cur = root;
		stk.push(cur);
		while (!stk.empty()) {
			cur = stk.top();
			if (cur) {
				stk.pop();
				if (cur->right) stk.push(cur->right);
				if (cur->left) stk.push(cur->left);
				stk.push(cur);
				stk.push(nullptr);
			}
			else {
				stk.pop();
				result.push_back(stk.top()->val);
				stk.pop();
			}
		}
		return result;
	}
};

 后序遍历

class Solution {
public:
	vector<int> postorderTraversal(TreeNode* root) {
		if (!root) return vector<int> {};
		vector<int> result;
		stack<TreeNode*> stk;
		TreeNode* cur = root;
		stk.push(cur);
		while (!stk.empty()) {
			cur = stk.top();
			if (cur) {
				stk.pop();
				stk.push(cur);
				stk.push(nullptr);
				if (cur->right) stk.push(cur->right);
				if (cur->left) stk.push(cur->left);
			}
			else {
				stk.pop();
				result.push_back(stk.top()->val);
				stk.pop();
			}
		}
		return result;
	}
};

中序遍历

class Solution {
public:
	vector<int> inorderTraversal(TreeNode* root) {
		if (!root) return vector<int> {};
		vector<int> result;
		stack<TreeNode*> stk;
		TreeNode* cur = root;
		stk.push(cur);
		while (!stk.empty()) {
			cur = stk.top();
			if (cur) {
				stk.pop();
				if (cur->right) stk.push(cur->right);
				stk.push(cur);
				stk.push(nullptr);
				if (cur->left) stk.push(cur->left);
			}
			else {
				stk.pop();
				result.push_back(stk.top()->val);
				stk.pop();
			}
		}
		return result;
	}
};

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值