二叉树的深度优先和广度优先遍历
来源:互联网 发布:网络劫持金山毒霸 编辑:程序博客网 时间:2024/04/29 16:12
图的深度优先搜索法是树的先根遍历的推广
它的基本思想是:从图G的某个顶点v0出发,访问v0,然后选择一个与v0相邻且没被访问过的顶点vi访问,再 从vi出发选择一个与vi相邻且未被访问的顶点vj进行访问,依次继续。如果当前被访问过的顶点的所有邻接顶点都已被访问,则退回到已被访问的顶点序列中 最后一个拥有未被访问的相邻顶点的顶点w,从w出发按同样的方法向前遍历,直到图中所有顶点都被访问。
图的广度优先搜索是树的按层次遍历的推广
它的基本思想是:首先访问初始点vi,并将其标记为已访问过,接着访问vi的所有未被访问过的邻接点 vi1,vi2, …, vi t,并均标记已访问过,然后再按照vi1,vi2, …, vi t的次序,访问每一个顶点的所有未被访问过的邻接点,并均标记为已访问过,依次类推,直到图中所有和初始点vi有路径相通的顶点都被访问过为止。
二叉树的深度优先遍历的非递归的通用做法是采用栈,广度优先遍历的非递归的通用做法是采用队列。
template <class T>bool CBintree<T>::Depth_RF() //先根深度遍历{ cout << "先根遍历序列:\n"; stack <TreeNode> s; s.push(*m_pBintree); while (!s.empty()) { TreeNode node_s = s.top(); cout << node_s.va << "\n"; s.pop(); if (node_s.prchild != NULL) { s.push(*node_s.prchild); } if (node_s.plchild != NULL) { s.push(*node_s.plchild); } } return true;}
template <class T>bool CBintree<T>::Depth_RM() //中根深度遍历{ cout << "中根遍历序列:\n"; stack <TreeNode> s; TreeNode *pNode = m_pBintree; while (pNode != NULL || !s.empty()) { while (pNode != NULL) { s.push(*pNode); pNode = pNode->plchild; } if (!s.empty()) { TreeNode node_s = s.top(); cout << node_s.va << "\n"; s.pop(); pNode = node_s.prchild; } } return true;}
template <class T>bool CBintree<T>::WidthFS() //层次遍历{ cout << "层次遍历序列:\n"; queue <TreeNode> q; q.push(*m_pBintree); while (!q.empty()) { TreeNode *pNode = &q.front(); cout << pNode->va << "\n"; if (pNode->plchild != NULL) { q.push(*pNode->plchild); } if (pNode->prchild != NULL) { q.push(*pNode->prchild); } q.pop(); } return true;}
教科书标准算法及优化算法
先序遍历非递归算法
void PreOrderUnrec(Bitree *t){ Stack s; StackInit(s); Bitree *p=t; while (p!=NULL || !StackEmpty(s)) { while (p!=NULL) //遍历左子树 { visite(p->data); push(s,p); p=p->lchild; } if (!StackEmpty(s)) //通过下一次循环中的内嵌while实现右子树遍历 { p=pop(s); p=p->rchild; }//endif }//endwhile }
中序遍历非递归算法
void InOrderUnrec(Bitree *t){ Stack s; StackInit(s); Bitree *p=t; while (p!=NULL || !StackEmpty(s)) { while (p!=NULL) //遍历左子树 { push(s,p); p=p->lchild; } if (!StackEmpty(s)) { p=pop(s); visite(p->data); //访问根结点 p=p->rchild; //通过下一次循环实现右子树遍历 }//endif }//endwhile}
后序遍历非递归算法
typedef enum{L,R} tagtype;typedef struct{ Bitree ptr; tagtype tag;}stacknode;typedef struct{ stacknode Elem[maxsize]; int top;}SqStack;void PostOrderUnrec(Bitree t){ SqStack s; stacknode x; StackInit(s); p=t; do { while (p!=null) //遍历左子树 { x.ptr = p; x.tag = L; //标记为左子树 push(s,x); p=p->lchild; } while (!StackEmpty(s) && s.Elem[s.top].tag==R) { x = pop(s); p = x.ptr; visite(p->data); //tag为R,表示右子树访问完毕,故访问根结点 } if (!StackEmpty(s)) { s.Elem[s.top].tag =R; //遍历右子树 p=s.Elem[s.top].ptr->rchild; } }while (!StackEmpty(s));}//PostOrderUnrec
前序最简洁非递归算法
void PreOrderUnrec(Bitree *t){ Bitree *p; Stack s; s.push(t); while (!s.IsEmpty()) { s.pop(p); visit(p->data); if (p->rchild != NULL) s.push(p->rchild); if (p->lchild != NULL) s.push(p->lchild); }}
后序算法之二
void BT_PostOrderNoRec(pTreeT root){ stack<treeT *> s; pTreeT pre=NULL; while ((NULL != root) || !s.empty()) { if (NULL != root) { s.push(root); root = root->left; } else { root = s.top(); if (root->right!=NULL && pre!=root->right){ root=root->right; } else{ root=pre=s.top(); visit(root); s.pop(); root=NULL; } } }}
0 0
- 二叉树的深度优先遍历和广度优先遍历
- 二叉树的深度优先遍历和广度优先遍历
- 二叉树的深度优先遍历和广度优先遍历
- 二叉树的深度优先遍历和广度优先遍历
- 二叉树的深度优先遍历和广度优先遍历
- 二叉树的深度优先遍历和广度优先遍历
- 二叉树的广度优先遍历和深度优先遍历
- 二叉树的深度优先遍历和广度优先遍历
- 二叉树的深度优先遍历和广度优先遍历
- 二叉树的深度优先遍历和广度优先遍历
- 二叉树的深度优先遍历和广度优先遍历
- 二叉树的深度优先遍历和广度优先遍历
- 二叉树的深度优先遍历和广度优先遍历
- 二叉树的深度优先遍历和广度优先遍历
- 二叉树的深度优先遍历和广度优先遍历
- 二叉树的深度优先遍历和广度优先遍历
- 二叉树的深度优先遍历和广度优先遍历
- 二叉树的深度优先遍历和广度优先遍历
- 开发手记9.10
- Android ---js与java的相互调用
- ios 获取应用唯一标识
- Javascript 的 Attribute 方法
- java常见内存溢出(OOM)解决方案
- 二叉树的深度优先和广度优先遍历
- ActiveMQ的queue以及topic两种消息处理机制分析
- 转载巧用FPGA中资源
- RichEdit 取消全选
- MBR&GPT硬盘分区类型&属性详解(Win下更改/设置OEM/恢复分区方法)
- Centos 6.6 install gcc-4.8.2
- 升级android sdk到5.0,创建项目错误解决方法
- 我在学习爬虫(二)
- SQL 2000挂马的批量替换