//設 T 是一棵具有 n 個節點的二叉樹,若給定二叉樹 T 的先序序列和中序序列,並假設 T 的先序序列和中序序列分別放在數組 PreOrder[1..n]和 InOrder[1..n ]中,設計一個構造二叉樹 T 的鏈式存儲結構的算法。 #include <iostream> #include <stack> #include <queue> #include <string> using namespace std; #define TElemType int #define max 1024 typedef struct BiTNode{ TElemType data; struct BiTNode *lchild, *rchild; }BiTNode, *BiTree; //設 T 的先序序列和中序序列分別放在數組 PreOrder[1..n]和 InOrder[1..n ]中,根據先序遍 歷的特點可知,PreOrder[1]為根節點,設中序序列中 InOrder[i]=PreOrder[1],則在 InOrder[i] 的左面的 InOrder[1..i-1]應為二叉樹的左子樹,而 InOrder[i+1..n]為根的右子樹。相對應的是, 在先序序列中根的左子樹應為 PreOrder[2..i],而右子樹為 PreOrder[i+1..n]。而左子樹的根為 PreOrder[2],右子樹的根為 PreOrder[i+1]。依次遞歸,用同樣的方法可以確定子樹的左子樹 和右子樹,從而逐步確定整個二叉樹 //遞歸 // 左子樹 右子樹 //先序 i1+1 -> i1+i-i2 i1+i+1-i2->j1 //后序 i2 -> i-1 i+1 -> j2 //這里因為T在函數內部還會改變,所以需要加個引用(也可以理解為二重指針) void CreateTree(BiTree &T, TElemType preorder[], int i1, int j1, TElemType inorder[], int i2, int j2){ int i=i2; //先建立i,用於后續定位中序序列中的局部根結點位置 if(i1<=j1){ T=(BiTree) malloc(sizeof(BiTNode)); T->data=preorder[i1]; //先序遍歷的第一個結點為根結點 // cout<<"add "<<T<<endl; T->lchild=NULL; T->rchild=NULL; while(inorder[i]!=preorder[i1]) i++; //找到根結點在中序遍歷中的位置,以此左為左子樹,右為右子樹 // cout<<"tag"<<endl; CreateTree(T->lchild, preorder, i1+1, i1+i-i2, inorder, i2, i-1); //遍歷左右子樹 CreateTree(T->rchild, preorder, i1+i+1-i2, j1, inorder, i+1, j2); } else T=NULL; } int main(){ int preorder[7]={0,1,2,4,5,3,6}; int inorder[7]={0,4,2,5,1,6,3}; BiTree S=(BiTree) malloc(sizeof(BiTNode)); CreateTree(S, preorder, 1, 6, inorder, 1, 6); queue<BiTree> q; q.push(S); cout<<"以層次遍歷訪問此樹"<<endl; while(!q.empty()){ BiTree t=q.front(); q.pop(); cout<<t->data<<endl; if(t->lchild!=NULL) q.push(t->lchild); if(t->rchild) q.push(t->rchild); } }