二叉树的遍历方式(递归和非递归版本)
二叉树结构体:
struct BinaryTreeNode { int m_nValue; BinaryTreeNode* m_pLeft; BinaryTreeNode* m_pRight; };
二叉树创建:
BinaryTreeNode* CreateBinaryTreeNode(int value) { BinaryTreeNode* pNode = new BinaryTreeNode(); pNode->m_nValue = value; pNode->m_pLeft = NULL; pNode->m_pRight = NULL; return pNode; }
打印二叉树:
void PrintTreeNode(BinaryTreeNode* pNode) { if(pNode != NULL) { printf("value of this node is: %d\n", pNode->m_nValue); if(pNode->m_pLeft != NULL) printf("value of its left child is: %d.\n", pNode->m_pLeft->m_nValue); else printf("left child is null.\n"); if(pNode->m_pRight != NULL) printf("value of its right child is: %d.\n", pNode->m_pRight->m_nValue); else printf("right child is null.\n"); } else { printf("this node is null.\n"); } printf("\n"); } void PrintTree(BinaryTreeNode* pRoot) { PrintTreeNode(pRoot); if(pRoot != NULL) { if(pRoot->m_pLeft != NULL) PrintTree(pRoot->m_pLeft); if(pRoot->m_pRight != NULL) PrintTree(pRoot->m_pRight); } }
销毁二叉树:
void DestroyTree(BinaryTreeNode* pRoot) { if(pRoot != NULL) { BinaryTreeNode* pLeft = pRoot->m_pLeft; BinaryTreeNode* pRight = pRoot->m_pRight; delete pRoot; pRoot = NULL; DestroyTree(pLeft); DestroyTree(pRight); } }
遍历方式(前序、中序、后序):
//前序遍历 根节点->左节点->右节点 void pre_traverse(BinaryTreeNode* pRoot) { if (pRoot) { printf(" %d", pRoot->m_nValue); if (pRoot->m_pLeft) pre_traverse(pRoot->m_pLeft); if (pRoot->m_pRight) pre_traverse(pRoot->m_pRight); } } //前序遍历的非递归实现 void pre_traverse_stack(BinaryTreeNode* pRoot) { if (NULL == pRoot) return; stack<BinaryTreeNode*> Bnode; BinaryTreeNode* node_pop = NULL; //保存出栈节点 BinaryTreeNode* pcurrent = pRoot; //访问当前节点 //直至当前节点为空或栈为空时,结束循环 while (pcurrent||!Bnode.empty()) { //若左子结点非空,则不断输出左子结点数值 while (pcurrent) { printf(" %d", pcurrent->m_nValue); Bnode.push(pcurrent); pcurrent = pcurrent->m_pLeft; } //记录父节点,顶出父节点,对父节点的右节点进行操作 if (!Bnode.empty()) { pcurrent = Bnode.top(); Bnode.pop(); pcurrent = pcurrent->m_pRight; } } } //中序遍历 左节点->根节点->右节点 void mid_traverse(BinaryTreeNode* pRoot) { if (pRoot) { if (pRoot->m_pLeft) mid_traverse(pRoot->m_pLeft); printf(" %d", pRoot->m_nValue); if (pRoot->m_pRight) mid_traverse(pRoot->m_pRight); } } //中序遍历的非递归版本 void mid_traverse_stack(BinaryTreeNode* pRoot) { if (NULL == pRoot) return; stack<BinaryTreeNode*> Bnode; BinaryTreeNode* pcurrent = pRoot; //访问当前节点 while (pcurrent || !Bnode.empty()) { while (pcurrent) { Bnode.push(pcurrent); pcurrent = pcurrent->m_pLeft; } if (!Bnode.empty()) { pcurrent = Bnode.top(); printf(" %d", pcurrent->m_nValue); Bnode.pop(); pcurrent = pcurrent->m_pRight; } } } //后续遍历 左节点->右节点->根节点 void beh_traverse(BinaryTreeNode* pRoot) { if (pRoot) { if (pRoot->m_pLeft) beh_traverse(pRoot->m_pLeft); if (pRoot->m_pRight) beh_traverse(pRoot->m_pRight); printf(" %d", pRoot->m_nValue); } } //后序遍历的非递归版本 void beh_traverse_stack(BinaryTreeNode* pRoot) { if (NULL == pRoot) return; stack<BinaryTreeNode*> Bnode; BinaryTreeNode* pre_node = NULL; //前次访问节点 BinaryTreeNode* pcurrent = NULL; //访问当前节点 Bnode.push(pRoot); while (!Bnode.empty()) { pcurrent = Bnode.top(); //如果当前节点没有子节点或者子节点已经被访问过,则输出其相应数值 if ((pcurrent->m_pLeft == NULL&&pcurrent->m_pRight == NULL) || (pre_node != NULL && (pre_node == pcurrent->m_pLeft || pre_node == pcurrent->m_pRight))) { printf(" %d", pcurrent->m_nValue); Bnode.pop(); pre_node = pcurrent; } else { if (pcurrent->m_pRight) Bnode.push(pcurrent->m_pRight); if (pcurrent->m_pLeft) Bnode.push(pcurrent->m_pLeft); } } }