树结构
TreeNode结构:
1 2 3 4 5 6
| struct TreeNode{ int val; TreeNode* left; TreeNode* right; TreeNode(int x):val(x),left(NULL),right(NULL) {} };
|
二叉树:由一个根节点及两颗不相交的二叉树组成。
满二叉树:每一个结点或者是一个分支结点,并恰好有两个非空的子节点。
飞空满二叉树的叶结点数等于其分支结点数+1。
完全二叉树:严格的形状要求,从根节点起每一层从左到右填充。一棵高度为d的完全二叉树,除了d-1层以外,每一层都是满的。(完全二叉树不一定是满二叉树)
遍历
普通递归遍历
前序遍历,中序遍历,后序遍历
1 2 3 4 5 6
| void travel_preoder0(TreeNode* root){ if (!root) return; cout<<root->val<<endl; travel_preoder0(root->left); travel_preoder0(root->right); }
|
如果要返回遍历结果的话,存vector
1 2 3 4 5 6 7 8 9
| vector<int> res; vector<int> travel_preorder1(TreeNode* root){ if(root != NULL){ res.push_back(root->val); travel_preorder1(root->left); travel_preorder1(root->right); } return res; }
|
用stack辅助前序遍历:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17
| void travel_preoder2(TreeNode* root){ stack<TreeNode*> Stk; if (root) { Stk.push(root); } while (!Stk.empty()) { root = Stk.top(); cout<<root->val<<endl; Stk.pop(); if (root->right) { Stk.push(root->right); } if (root->left) { Stk.push(root->left); } } }
|
由于stack是先入后出,前序遍历的话,root访问之后,先将right右结点放入stack里,再将left左子节点放入stack。但这样写不好写中序遍历和后序遍历的。
迭代前序遍历算法
注意节点入stack的顺序
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59
|
vector<int> preorderTraversal(TreeNode* root){ vector<int> ans; stack<TreeNode*> stk; TreeNode* rt = root; while (rt || stk.size()) { while (rt) { stk.push(rt->right); ans.push_back(rt->val); rt = rt->left; } rt = stk.top(); stk.pop(); } return ans; }
vector<int> postorderTraversal(TreeNode* root) { stack<TreeNode*> S; vector<int> v; TreeNode* rt = root; while(rt || S.size()){ while(rt){ S.push(rt->left); v.push_back(rt->val); rt=rt->right; } rt=S.top(); S.pop(); } reverse(v.begin(),v.end()); return v; }
vector<int> inorderTraversal(TreeNode* root){ stack<TreeNode*> S; vector<int> v; TreeNode* rt = root; while (rt || S.size()) { while (rt) { S.push(rt); rt = rt->left; } rt = S.top(); S.pop(); v.push_back(rt->val); rt = rt->right; } return v; }
|
层次遍历
逐层遍历,先根再左边右边逐层访问下来。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18
| void PrintFromTopToBottom(TreeNode* root){ if (!root) { return; } queue<TreeNode*> DequeTreeNode; DequeTreeNode.push(root); while (!DequeTreeNode.empty()) { TreeNode* pNode = DequeTreeNode.front(); DequeTreeNode.pop(); cout<<pNode->val<<endl; if (pNode->left) { DequeTreeNode.push(pNode->left); } if (pNode->right) { DequeTreeNode.push(pNode->right); } } }
|