DATA STRUCTURES 5 n n n n n

  • Slides: 113
Download presentation
DATA STRUCTURES 第 5章 树 树和森林的概念 n 二叉树的表示 n 二叉树遍历及其应用 n 线索化二叉树 n 树与森林

DATA STRUCTURES 第 5章 树 树和森林的概念 n 二叉树的表示 n 二叉树遍历及其应用 n 线索化二叉树 n 树与森林 n 堆 n Huffman树 n Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES 自由树 Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES 自由树 Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES 树的示意图( P. 187) Department of Computer Science & Technology, Nanjing University fall

DATA STRUCTURES 树的示意图( P. 187) Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES 树的特点 • 每棵子树的根结点有且仅有一个直接前驱, 但可以有0个或多个直接后继。 0层 A B E K C F L

DATA STRUCTURES 树的特点 • 每棵子树的根结点有且仅有一个直接前驱, 但可以有0个或多个直接后继。 0层 A B E K C F L G 1层 D H M I J 2层 height =3 3层 Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES 术语 n n 结点 结点的度 分支结点 叶结点 n n n 子女 双亲

DATA STRUCTURES 术语 n n 结点 结点的度 分支结点 叶结点 n n n 子女 双亲 兄弟 祖先 子孙 结点层次 n n n E K C F L G n n 树的度 树高度 森林 0层 A B n 1层 D H M I J 2层 height =3 3层 Department of Computer Science & Technology, Nanjing University fall 2009

树的抽象数据类型 DATA STRUCTURES template <class Type> class Tree { public: Tree ( ); ~Tree

树的抽象数据类型 DATA STRUCTURES template <class Type> class Tree { public: Tree ( ); ~Tree ( ); position Root ( ); Build. Root ( const Type& value ); position First. Child ( position p ); position Next. Sibling ( position p ); position Parent ( position p ); Type Get. Data ( position p ); int Insert. Child ( const position p, const Type &value ); int Delete. Child ( position p, int i ); Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES L R 二叉树的五种不同形态 Department of Computer Science & Technology, Nanjing University fall

DATA STRUCTURES L R 二叉树的五种不同形态 Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES 满二叉树 完全二叉树 • 层次h,叶结点仅在 h和h-1 两层出 现 • 对任一结点,若其右子树的高度为 k,则其左子树的高度是 k or

DATA STRUCTURES 满二叉树 完全二叉树 • 层次h,叶结点仅在 h和h-1 两层出 现 • 对任一结点,若其右子树的高度为 k,则其左子树的高度是 k or k+1 Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES • 性质 4 具有 n (n 0) 个结点的完全二叉树的高 度为 log 2(n+1) 23

DATA STRUCTURES • 性质 4 具有 n (n 0) 个结点的完全二叉树的高 度为 log 2(n+1) 23 -1 24 -1 Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES (4)若结点编号i为奇数,且i!=1, 则它的左兄 弟为结点i-1。 (5)若结点编号i为偶数,且i!=n, 则它的右兄 弟为结点i+1。 (6)结点i所在层次为 log 所在层次为 2 i +1

DATA STRUCTURES (4)若结点编号i为奇数,且i!=1, 则它的左兄 弟为结点i-1。 (5)若结点编号i为偶数,且i!=n, 则它的右兄 弟为结点i+1。 (6)结点i所在层次为 log 所在层次为 2 i +1 1 2 4 3 5 6 7 8 9 10 Department of Computer Science & Technology, Nanjing University fall 2009

二叉树的抽象数据类型 DATA STRUCTURES template <class Type> class Binary. Tree { public: Binary. Tree (

二叉树的抽象数据类型 DATA STRUCTURES template <class Type> class Binary. Tree { public: Binary. Tree ( ); //构造函数 Binary. Tree ( Bin. Tree. Node<Type> * lch, Bin. Tree. Node<Type> * rch, Type item ); //构造以item为根,lch和rch为左、右 //子树的二叉树 int Is. Empty ( ); //判二叉树空否? Bin. Tree. Node<Type> * Parent ( ); //双亲 Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES Bin. Tree. Node<Type> * Left. Child ( ); //取左子女结点地址 Bin. Tree. Node<Type>

DATA STRUCTURES Bin. Tree. Node<Type> * Left. Child ( ); //取左子女结点地址 Bin. Tree. Node<Type> * Right. Child ( ); //取右子女结点地址 int Insert ( const Type& item ); //插入 int Find ( const Type &item ) const; //搜索 Type Get. Data ( ) const; //取得结点数据 Bin. Tree. Node<Type> *Get. Root ( ) const; //取根结点地址 } Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES 5. 3 二叉树的存储表示 • 顺序表示 完全二叉树 0 1 3 7 8 2

DATA STRUCTURES 5. 3 二叉树的存储表示 • 顺序表示 完全二叉树 0 1 3 7 8 2 4 5 6 9 0123456789 Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES 一般二叉树的顺序表示 0 1 2 3 7 5 8 0123 11 6 13

DATA STRUCTURES 一般二叉树的顺序表示 0 1 2 3 7 5 8 0123 11 6 13 5 6 7 8 9 11 13 Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES 极端情形: 只有右单支的二叉树 0 2 6 14 30 Department of Computer Science &

DATA STRUCTURES 极端情形: 只有右单支的二叉树 0 2 6 14 30 Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES 二叉树的链表表示 left. Child data right. Child left. Child 二叉链表 Department of Computer

DATA STRUCTURES 二叉树的链表表示 left. Child data right. Child left. Child 二叉链表 Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES left. Child data parent right. Child parent data right. Child left. Child

DATA STRUCTURES left. Child data parent right. Child parent data right. Child left. Child 三叉链表 Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES root A A B C A B C D E root F

DATA STRUCTURES root A A B C A B C D E root F B D E F 二叉链表 C E D F 三叉链表 二叉树链表表示的示例 Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES root A B C D E F data parent left. Child right.

DATA STRUCTURES root A B C D E F data parent left. Child right. Child 0 1 2 3 4 5 A B C D E F -1 0 1 1 3 3 1 2 -1 4 -1 -1 -1 3 -1 5 -1 -1 二叉链表的静态结构 Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES 二叉树的类定义 template <class Type> class Binary. Tree; template <class Type> Class Bin.

DATA STRUCTURES 二叉树的类定义 template <class Type> class Binary. Tree; template <class Type> Class Bin. Tree. Node { friend class Binary. Tree<Type>; private: Type data; Bin. Tree. Node<Type> * left. Child; Bin. Tree. Node<Type> * right. Child; public: Bin. Tree. Node ( ) : left. Child (NULL), right. Child (NULL) { } Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES Bin. Tree. Node ( Type item, Bin. Tree. Node<Type> *left = NULL,

DATA STRUCTURES Bin. Tree. Node ( Type item, Bin. Tree. Node<Type> *left = NULL, Bin. Tree. Node<Type> *right = NULL ) : data (item), left. Child (left), right. Child (right) { } Type Get. Data ( ) const { return data; } Bin. Tree. Node<Type> * Get. Left ( ) const { return left. Child; } Bin. Tree. Node<Type> * Get. Right ( ) const { return right. Child; } void Set. Data ( const Type& item ) { data = item; } Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES void Set. Left ( Bin. Tree. Node <Type> * L ) {

DATA STRUCTURES void Set. Left ( Bin. Tree. Node <Type> * L ) { left. Child = L; } void Set. Right ( Bin. Tree. Node <Type> * R ) { right. Child = R; } }; template <class Type> class Binary. Tree { private: Bin. Tree. Node <Type> *root; Type Ref. Value; void Create. Bin. Tree ( ifstream& in, Bin. Tree. Node<Type> * & current ); Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES Bin. Tree. Node<Type> * Parent ( Bin. Tree. Node<Type> * sub. Tree,

DATA STRUCTURES Bin. Tree. Node<Type> * Parent ( Bin. Tree. Node<Type> * sub. Tree, Bin. Tree. Node<Type> * current); int Insert (Bin. Tree. Node<Type> * & sub. Tree, const Type &item); //插入 void Traverse (Bin. Tree. Node<Type> *sub. Tree, ostream &out) const //遍历 int Find (Bin. Tree. Node<Type> *sub. Tree, const Type &item) const //搜索 void destroy (Bin. Tree. Node<Type> * sub. Tree); //删除 … } fall Department of Computer Science & Technology, Nanjing University 2009

DATA STRUCTURES 则可能的遍历次序有: 前序 VLR 中序 LVR 镜像 VRL 镜像 RVL 后序 LRV 镜像

DATA STRUCTURES 则可能的遍历次序有: 前序 VLR 中序 LVR 镜像 VRL 镜像 RVL 后序 LRV 镜像 RLV Department of Computer Science & Technology, Nanjing University fall 2009

中序遍历 (Inorder Traversal) DATA STRUCTURES LVR - + a / e * b c

中序遍历 (Inorder Traversal) DATA STRUCTURES LVR - + a / e * b c 遍历结果: f d a+b*c-d-e/f Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES 中序遍历二叉树算法的框架是: n 若二叉树为空,则空操作; n 否则 u 中序遍历左子树 (L); u 访问根结点 (V); u

DATA STRUCTURES 中序遍历二叉树算法的框架是: n 若二叉树为空,则空操作; n 否则 u 中序遍历左子树 (L); u 访问根结点 (V); u 中序遍历右子树 (R)。 Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES 二叉树递归的中序遍历算法 template <class Type> void Binary. Tree <Type> : : In. Order

DATA STRUCTURES 二叉树递归的中序遍历算法 template <class Type> void Binary. Tree <Type> : : In. Order ( Bin. Tree. Node <Type> *sub. Tree ) { if ( sub. Tree != NULL ) { In. Order ( sub. Tree->left. Child ); cout << sub. Tree->data; In. Order ( sub. Tree->right. Child ); } } Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES 前序遍历 (Preorder Traversal) VLR - + a / e * b 遍历结果:

DATA STRUCTURES 前序遍历 (Preorder Traversal) VLR - + a / e * b 遍历结果: f c d -+a*b-cd/ef Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES 前序遍历二叉树算法的框架是: n 若二叉树为空,则空操作; n 否则 u 访问根结点 (V); u 前序遍历左子树 (L); u

DATA STRUCTURES 前序遍历二叉树算法的框架是: n 若二叉树为空,则空操作; n 否则 u 访问根结点 (V); u 前序遍历左子树 (L); u 前序遍历右子树 (R)。 Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES 二叉树递归的前序遍历算法 template <class Type> void Binary. Tree<Type> : : Pre. Order (

DATA STRUCTURES 二叉树递归的前序遍历算法 template <class Type> void Binary. Tree<Type> : : Pre. Order ( Bin. Tree. Node <Type> * sub. Tree ) { if ( sub. Tree != NULL ) { cout << sub. Tree->data; Pre. Order ( sub. Tree->left. Child ); Pre. Order ( sub. Tree->right. Child ); } } Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES 后序遍历 (Postorder Traversal) LRV - + a / e * b c

DATA STRUCTURES 后序遍历 (Postorder Traversal) LRV - + a / e * b c 遍历结果: f d abcd-*+ef/Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES 后序遍历二叉树算法的框架是: n 若二叉树为空,则空操作; n 否则 u 后序遍历左子树 (L); u 后序遍历右子树 (R); u

DATA STRUCTURES 后序遍历二叉树算法的框架是: n 若二叉树为空,则空操作; n 否则 u 后序遍历左子树 (L); u 后序遍历右子树 (R); u 访问根结点 (V)。 Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES 二叉树递归的后序遍历算法 template <class Type> void Binary. Tree <Type> : : Post. Order

DATA STRUCTURES 二叉树递归的后序遍历算法 template <class Type> void Binary. Tree <Type> : : Post. Order ( Bin. Tree. Node <Type> * sub. Tree ) { if ( sub. Tree != NULL ) { Post. Order ( sub. Tree->left. Child ); Post. Order ( sub. Tree->right. Child ); cout << sub. Tree->data; } } Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES template <class Type> void Binary. Tree <Type>: : In. Order ( )

DATA STRUCTURES template <class Type> void Binary. Tree <Type>: : In. Order ( ) { In. Order ( root ); } template <class Type> void Binary. Tree <Type>: : Pre. Order ( ) { Pre. Order ( root ); } template <class Type> void Binary. Tree <Type>: : Post. Order ( ) { Post. Order ( root ); } Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES 应用二叉树遍历的实例 1. 利用二叉树后序遍历计算二叉树结点个数 template <class Type> int Binary. Tree<Type> : : Count

DATA STRUCTURES 应用二叉树遍历的实例 1. 利用二叉树后序遍历计算二叉树结点个数 template <class Type> int Binary. Tree<Type> : : Count ( Bin. Tree. Node <Type> * t ) const { if ( t == NULL ) return 0; else return 1 + Count ( t->left. Child ) + Count ( t->right. Child ); } Department of Computer Science & Technology, Nanjing University fall 2009

层次序遍历二叉树的算法 DATA STRUCTURES 层次序遍历二叉树就是从根结点开始,按层 次逐层遍历 n + a / e * b f c

层次序遍历二叉树的算法 DATA STRUCTURES 层次序遍历二叉树就是从根结点开始,按层 次逐层遍历 n + a / e * b f c d 遍历顺序 Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES Q a c b d e 访问a, 进队 b c a出队 访问b,

DATA STRUCTURES Q a c b d e 访问a, 进队 b c a出队 访问b, 进队 访问c, 进队 Q c d Q Q b出队 访问d, 进队 e c出队 访问e, 进队 e d出队 e出队 Department of Computer Science & Technology, Nanjing University fall 2009

层次序遍历的(非递归)算法 DATA STRUCTURES template <class T> void Binary. Tree<T>: : level. Order (void (*visit)

层次序遍历的(非递归)算法 DATA STRUCTURES template <class T> void Binary. Tree<T>: : level. Order (void (*visit) (Bin. Tree. Node<T> *t)) { if (root == NULL) return; Queue<Bin. Tree. Node<T> * > Q; Bin. Tree. Node<T> *p = root; visit (p); Q. En. Queue (p); while (!Q. Is. Empty ()) { Q. De. Queue (p); if (p->left. Child != NULL) { visit (p->left. Child); Q. En. Queue (p->left. Child); } if (p->right. Child != NULL) { visit (p->right. Child); Q. En. Queue (p->right. Child); } } }; Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES 5. 5 线索二叉树 Department of Computer Science & Technology, Nanjing University fall

DATA STRUCTURES 5. 5 线索二叉树 Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES 线索 (Thread):指示前驱和后继的指针 线索化二叉树(Threaded Binary Tree): 加了线索的二叉树 Department of Computer Science & Technology,

DATA STRUCTURES 线索 (Thread):指示前驱和后继的指针 线索化二叉树(Threaded Binary Tree): 加了线索的二叉树 Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES 线索化二叉树及其二叉链表表示 Left. Child data Right. Child Left. Thread Right. Thread Left. Thread=0,

DATA STRUCTURES 线索化二叉树及其二叉链表表示 Left. Child data Right. Child Left. Thread Right. Thread Left. Thread=0, Left. Thread=1, Right. Thread=0, Right. Thread=1, Left. Child为左子女指针 Left. Child为前驱线索 Right. Child为右子女指针 Right. Child为后继指针 Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES 中序线索化二叉树的例子 线索化二叉树 Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES 中序线索化二叉树的例子 线索化二叉树 Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES 带表头结点的中序穿线链表 原来的 线索化 二叉树 成为表 头结点 的左子 树 Department of Computer Science

DATA STRUCTURES 带表头结点的中序穿线链表 原来的 线索化 二叉树 成为表 头结点 的左子 树 Department of Computer Science & Technology, Nanjing University fall 2009

中序线索化二叉树的类定义 DATA STRUCTURES template <class Type> class Thread. Tree; template <class Type> class Thread.

中序线索化二叉树的类定义 DATA STRUCTURES template <class Type> class Thread. Tree; template <class Type> class Thread. Node { friend class Thread. Tree<Type>; private: int left. Thread, right. Thread; Thread. Node<Type> *left. Child, *right. Child; Type data; public: Thread. Node ( const Type item ) : data (item), left. Child (NULL), right. Child (NULL), left. Thread (0), right. Thread (0) { } }; Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES template <class Type> class Thread. Tree { private: Thread. Node<Type> * root;

DATA STRUCTURES template <class Type> class Thread. Tree { private: Thread. Node<Type> * root; //根 In. Thread ( Thread. Node <Type> * current, Thread. Node <Type> * &pre ); //建树 public: Thread. Tree ( ) : root (NULL) { }; //构造函数 Thread. Node<Type> * First ( Thread. Node <Type> * current ); Thread. Node<Type> * Last ( Thread. Node <Type> * current ); Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES Thread. Node<Type> * Next ( Thread. Node <Type> * current ); Thread.

DATA STRUCTURES Thread. Node<Type> * Next ( Thread. Node <Type> * current ); Thread. Node<Type> * Prior ( Thread. Node <Type> * current ); ………… } Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES 寻找当前结点在中序下的后继 A B D E G J if (current->right. Thread ==1) 后继为current->right.

DATA STRUCTURES 寻找当前结点在中序下的后继 A B D E G J if (current->right. Thread ==1) 后继为current->right. Child C else //current->right. Thread != 1 后继为当前结点右子树 F 的中序下的第一个结点 (最左下) H I K Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES 寻找当前结点在中序下的前驱 A B D C E G F H J I if

DATA STRUCTURES 寻找当前结点在中序下的前驱 A B D C E G F H J I if (current->left. Thread==1) 前驱为current->left. Child else //current->left. Thread==0 前驱为当前结点左子树 中序下的最后一个结点 (最右下) K L Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES 5. 6 树与森林 树的存储表示 树的广义表表示 n A B E 叶 结 点

DATA STRUCTURES 5. 6 树与森林 树的存储表示 树的广义表表示 n A B E 叶 结 点 C F 根 结 D 点 广义表 表头结点 G 分支结点 子表结点 原子结点 Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES 双亲表示法(每个节点都有唯一的双亲节点) n A B E C F D 0 1 2 3

DATA STRUCTURES 双亲表示法(每个节点都有唯一的双亲节点) n A B E C F D 0 1 2 3 4 5 6 data A B C D E F G parent -1 0 0 0 1 1 3 G Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES   n子女指针表示法 data child 1 child 2 child 3 A A B

DATA STRUCTURES   n子女指针表示法 data child 1 child 2 child 3 A A B E C F childd D B C D G G E F 每个结点包含的指针个数相等,等于树的度(degre 适用于: 等数量的链域 Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES n 子女链表表示 A B E C F 0 A 1 B D

DATA STRUCTURES n 子女链表表示 A B E C F 0 A 1 B D 2 C ∧ G 3 D 4 E ∧ 1 4 2 5∧ 3∧ 6∧ 5 F ∧ 6 G ∧ • 无序树情形链表中各结点顺序任意,有序 树必须自左向右链接各个子女结点。 Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES 左子女-右兄弟表示 n data first. Child next. Sibling A^ B A B E

DATA STRUCTURES 左子女-右兄弟表示 n data first. Child next. Sibling A^ B A B E C F D G ^E ^C D^ ^F ^ ^G ^ Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES 森林与二叉树的转换 树 ————二叉树(左子女,右兄弟) 森林: 树的有限集合 Department of Computer Science & Technology, Nanjing University

DATA STRUCTURES 森林与二叉树的转换 树 ————二叉树(左子女,右兄弟) 森林: 树的有限集合 Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES T 1 A T 2 F B C D G E T

DATA STRUCTURES T 1 A T 2 F B C D G E T 3 H I A J C K B T 2 F T 3 H G I C K D E F D 3 棵树的森林 T 1 A B E I K J H G J 森林的二叉树表示 各棵树的二叉树表示 Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES 树的遍历 • 深度优先遍历 – 先根(前序)次序遍历 – 后根(后序)次序遍历 A B E C F

DATA STRUCTURES 树的遍历 • 深度优先遍历 – 先根(前序)次序遍历 – 后根(后序)次序遍历 A B E C F D G Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES 树的先根次序遍历 当树非空时 n u u 访问根结点; 依次先根遍历根的各棵 子树。 先根遍历: A B E

DATA STRUCTURES 树的先根次序遍历 当树非空时 n u u 访问根结点; 依次先根遍历根的各棵 子树。 先根遍历: A B E C F A D G ABEFCDG B E C F 二叉树前序遍历 ? D G ABEFCDG Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES 树的先根遍历: • 与其对应二叉树表示的前序遍历结果相同。 • 可以借助对应二叉树的前序遍历算法实现。 Department of Computer Science & Technology, Nanjing

DATA STRUCTURES 树的先根遍历: • 与其对应二叉树表示的前序遍历结果相同。 • 可以借助对应二叉树的前序遍历算法实现。 Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES 树的后根次序遍历 n 当树非空时 依次后根遍历根的各棵子树; u 访问根结点。 u A B E C F

DATA STRUCTURES 树的后根次序遍历 n 当树非空时 依次后根遍历根的各棵子树; u 访问根结点。 u A B E C F 树后根遍历: EFBCGDA D G A B E 对应二叉树中序遍历 C F EFBCGDA Department of Computer Science & Technology, Nanjing University D G fall 2009

DATA STRUCTURES 树的后根遍历: 与其对应二叉树表示的中序遍历结果相同。 n 树的后根遍历可以借助对应二叉树的中 序遍历算法实现。 n Department of Computer Science & Technology,

DATA STRUCTURES 树的后根遍历: 与其对应二叉树表示的中序遍历结果相同。 n 树的后根遍历可以借助对应二叉树的中 序遍历算法实现。 n Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES • 广度优先(层次次序)遍历。 A A B E C F D G 按广度优先次序遍历树的结果。 ABCDEFG

DATA STRUCTURES • 广度优先(层次次序)遍历。 A A B E C F D G 按广度优先次序遍历树的结果。 ABCDEFG Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES 广度优先遍历算法 template <class Type> void Tree<Type> : : Level. Order ( )

DATA STRUCTURES 广度优先遍历算法 template <class Type> void Tree<Type> : : Level. Order ( ) { //按广度优先次序分层遍历树, 树的根结点是 //当前指针current。算法中用到一个队列。 Queue<Tree. Node<Type>*> Qu(Default. Size); Tree. Node<Type> *p; if ( current != NULL ) { //当前指针不空 p = current; //保存当前指针 Qu. En. Queue ( current ); while ( Qu. Is. Empty ( ) == 0 ) { Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES current = Qu. get. Front( ); Qu. De. Queue ( ); visit

DATA STRUCTURES current = Qu. get. Front( ); Qu. De. Queue ( ); visit ( ); //队列中取一个并访问之 current = current ->first. Child ; //待访问结点的子女结点进队列 while ( current != NULL ) { Qu. En. Queue ( current ); current = current->next. Sibling; } } current = p; //恢复算法开始的当前指针 } } Department of Computer Science & Technology, Nanjing University fall 2009

T 1 森林的后根次序遍历结果: BCEDA GF KIJH T 2 A F T 3 B C

T 1 森林的后根次序遍历结果: BCEDA GF KIJH T 2 A F T 3 B C D G DATA STRUCTURES H I E J K A B • 对应二叉树中序遍历的结果。 C F D E H G I K Department of Computer Science & Technology, Nanjing University J fall 2009

DATA STRUCTURES 5. 7 堆 ( Heap ) 优先级队列 每次出队列的是优先权最高的元素 Department of Computer Science

DATA STRUCTURES 5. 7 堆 ( Heap ) 优先级队列 每次出队列的是优先权最高的元素 Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES 堆的定义 0 9 17 23 45 87 78 65 78 87 53

DATA STRUCTURES 堆的定义 0 9 17 23 45 87 78 65 78 87 53 31 45 53 65 0 9 31 17 23 完全二叉树 顺序表示 Ki K 2 i+1 && Ki K 2 i+2 最小堆 完全二叉树 顺序表示 Ki K 2 i+1 && Ki K 2 i+2 最大堆 Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES 关于堆 堆:{k 0, k 1, …, kn-1}, ki k 2 i+1 &&

DATA STRUCTURES 关于堆 堆:{k 0, k 1, …, kn-1}, ki k 2 i+1 && ki k 2 i+2 完全二叉树: 所有非叶结点的值均不大于(或不小 于)其左、右孩子结点的值 Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES 判断下列序列是否是堆? {100, 90, 80, 60, 85, 75, 20, 25, 10, 70, 6

DATA STRUCTURES 判断下列序列是否是堆? {100, 90, 80, 60, 85, 75, 20, 25, 10, 70, 6 5, 50} Department of Computer Science & Technology, Nanjing University fall 2009

最小堆的类定义 #define Default. Size 10 template <class Type> class Min. Heap : public Min.

最小堆的类定义 #define Default. Size 10 template <class Type> class Min. Heap : public Min. PQ <Type> { private: Type * heap; //存放最小堆元素的数组 int Current. Size; //最小堆当前元素个数 int Max. Heap. Size; //最多允许元素个数 void Filter. Down ( int i, int m ); //从 i 到m自顶向下进行调整成为最小堆

void Filter. Up ( int i ); //从 i 到 0自底向上进行调整成为最小堆 public: Min. Heap

void Filter. Up ( int i ); //从 i 到 0自底向上进行调整成为最小堆 public: Min. Heap ( int sz ); //构造函数 : 建立空堆 Min. Heap ( Type arr[ ], int n ); //构造函数 Min. Heap ( const Min. Heap& R ); ~Min. Heap ( ) { delete [ ] heap; } int Insert ( const Type& x ); //插入 int Remove ( Type& x ); //删除

int Is. Empty ( ) const //判堆空否 { return Current. Size == 0; }

int Is. Empty ( ) const //判堆空否 { return Current. Size == 0; } int Is. Full ( ) const //判堆满否 { return Current. Size == Max. Heap. Size; } void Make. Empty ( ) { Current. Size = 0; } }

DATA STRUCTURES • 建立空堆 堆的建立 • 根据给定数组中的数据和大小, 建立堆对象 建 立 空 堆 template <class

DATA STRUCTURES • 建立空堆 堆的建立 • 根据给定数组中的数据和大小, 建立堆对象 建 立 空 堆 template <class Type> Min. Heap <Type> : : Min. Heap ( int max. Size ) { //根据给定大小max. Size, 建立堆对象 Max. Heap. Size = Default. Size < max. Size ? max. Size : Default. Size; //确定堆的大小 heap = new Type [Max. Heap. Size]; if ( heap == NULL ) { cerr << “存储分配错!” << endl; exit(1); } Current. Size = 0; } Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES • 根据给定数组中的数据和大小, 建立堆对象 template <class Type> Min. Heap <Type> : : Min.

DATA STRUCTURES • 根据给定数组中的数据和大小, 建立堆对象 template <class Type> Min. Heap <Type> : : Min. Heap ( Type arr[ ], int n ) { Max. Heap. Size = Default. Size < n ? n : Default. Size; heap = new Type [Max. Heap. Size]; if ( heap == NULL ) { cerr << “存储分配错!” << endl; exit(1); } for ( int i = 0; i < n; i++ ) //数组传送 heap[i] = arr[i]; Current. Size = n; //当前堆大小 Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES int current. Pos = (Current. Size-2)/2; //找最初调整位置: 最后的分支结点号 while ( current. Pos

DATA STRUCTURES int current. Pos = (Current. Size-2)/2; //找最初调整位置: 最后的分支结点号 while ( current. Pos >= 0 ) { //从下到上逐步扩大, 形成堆 Filter. Down ( current. Pos, Current. Size-1 ); //从current. Pos开始, 到Current. Size止, 53 //调整 current. Pos--; 17 78 i } } 23 65 87 45 09 Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES 例:将一组用数组存放的任意数据调整成堆 53 17 i 23 78 45 65 87 09 current. Pos

DATA STRUCTURES 例:将一组用数组存放的任意数据调整成堆 53 17 i 23 78 45 65 87 09 current. Pos = i = 3 Filter. Down逐步调整为最小堆 Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES 例:将一组用数组存放的任意数据调整成堆 53 17 i 23 53 78 45 65 17 87 09

DATA STRUCTURES 例:将一组用数组存放的任意数据调整成堆 53 17 i 23 53 78 45 65 17 87 09 09 i 78 45 65 87 23 current. Pos = i = 2 自下向上逐步调整为最小堆 Department of Computer Science & Technology, Nanjing University fall 2009

53 i 17 09 53 65 45 78 09 i 87 23 current. Pos

53 i 17 09 53 65 45 78 09 i 87 23 current. Pos = i = 1 17 23 65 45 78 87

i 53 09 17 09 i 53 09 65 45 78 87 23 current.

i 53 09 17 09 i 53 09 65 45 78 87 23 current. Pos = i = 0 17 23 65 45 78 87

09 09 i 53 17 23 17 17 65 45 78 87 23 i

09 09 i 53 17 23 17 17 65 45 78 87 23 i 5 3 65 45 78 87

DATA STRUCTURES template <class Type> void Min. Heap<Type> : : Filter. Down ( int

DATA STRUCTURES template <class Type> void Min. Heap<Type> : : Filter. Down ( int start, int End. Of. Heap ) { int i = start, j = 2*i+1; // j 是 i 的左子女 Type temp = heap[i]; while ( j <= End. Of. Heap ) { if ( j < End. Of. Heap && heap[j] > heap[j+1] ) j++; //两子女中选小者 if ( temp <= heap[j] ) break; else { heap[i] = heap[j]; //下面的上浮 i = j; j = 2*j+1; //向下滑动 } } heap[i] = temp; } Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES 最小堆的插入 最小堆的向上调整 17 i 23 5 3 09 i 09 65 45

DATA STRUCTURES 最小堆的插入 最小堆的向上调整 17 i 23 5 3 09 i 09 65 45 78 j 17 j 87 11 1123 5 3 65 45 78 87 23 在堆中插入新元素 11 Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES i i 1117 17 5 3 23 09 j 65 45 78

DATA STRUCTURES i i 1117 17 5 3 23 09 j 65 45 78 11 87 23 5 3 65 45 78 87 23 Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES template <class Type> int Min. Heap<Type> : : Insert ( const Type

DATA STRUCTURES template <class Type> int Min. Heap<Type> : : Insert ( const Type &x ) { //在堆中插入新元素 x if ( Current. Size == Max. Heap. Size ) //堆满 { cerr << "堆已满" << endl; return 0; } heap[Current. Size] = x; //插在表尾 Filter. Up (Current. Size); //向上调整为堆 Current. Size++; //堆元素增一 return 1; } Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES 最小堆的向上调整算法 template <class Type> void Min. Heap<Type> : : Filter. Up (

DATA STRUCTURES 最小堆的向上调整算法 template <class Type> void Min. Heap<Type> : : Filter. Up ( int start ) { //从 start 开始, 向上直到 0, 调整堆 int j = start, i = (j-1)/2; // i 是 j 的双亲 Type temp = heap[j]; while ( j > 0 ) { if ( heap[i] <= temp ) break; else { heap[j] = heap[i]; j = i; i = (i -1)/2; } } heap[j] = temp; } Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES 最小堆的删除算法(删除堆顶元素) • 将堆顶元素删去 • 以最后一个结点填补取走的元素; • 重新调整 Department of Computer Science &

DATA STRUCTURES 最小堆的删除算法(删除堆顶元素) • 将堆顶元素删去 • 以最后一个结点填补取走的元素; • 重新调整 Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES 最小堆的删除算法 template <class Type> int Min. Heap <Type> : : Remove (

DATA STRUCTURES 最小堆的删除算法 template <class Type> int Min. Heap <Type> : : Remove ( Type &x ) { if ( !Current. Size ) { cout << “ 堆已空 " << endl; return 0; } x = heap[0]; //最小元素出队列 heap[0] = heap[Current. Size-1]; Current. Size--; //用最小元素填补 Filter. Down ( 0, Current. Size-1 ); //调整 return 1; } Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES 算法分析: • Filter. Down(0, Current. Size-1) • Filter. Up(Current. Size) • 建堆操作

DATA STRUCTURES 算法分析: • Filter. Down(0, Current. Size-1) • Filter. Up(Current. Size) • 建堆操作 Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES 1 1 2 4 2 3 5 6 7 3 4 5

DATA STRUCTURES 1 1 2 4 2 3 5 6 7 3 4 5 6 8 7 8 树的路径长度 PL =? 0+1*2+2*4+3*1 = 13 树的路径长度 PL = 0+1*2+2*2+ +3*2+4*1 = 16 n 个结点的完全二叉树的路径长度: 下述数列前 n 项的和,即 Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES Huffman树 • 带权路径长度 (Weighted Path Length, WPL) 树的带权路径长度是树的各叶结点(外结 点)所带的权值与该结点到根的路径长度 的乘积的和。 2 4

DATA STRUCTURES Huffman树 • 带权路径长度 (Weighted Path Length, WPL) 树的带权路径长度是树的各叶结点(外结 点)所带的权值与该结点到根的路径长度 的乘积的和。 2 4 5 7 扩充二叉树 Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES 具有不同带权路径长度的扩充二叉树 2 2 4 5 7 WPL = 2*2+ 4*2+5*2+ 7*2 =

DATA STRUCTURES 具有不同带权路径长度的扩充二叉树 2 2 4 5 7 WPL = 2*2+ 4*2+5*2+ 7*2 = 36 7 4 5 5 7 2 4 WPL = 2*1+ WPL = 7*1+ 4*2+5*3+ 5*2+2*3+ 7*3 = 46 4*3 = 35 带权路径长度达到最小 Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES § 带权路径长度达到最小的扩充二叉树即为 Huffman树。 § 在Huffman树中,权值大的结点离根最近 7 5 2 4 Department of Computer

DATA STRUCTURES § 带权路径长度达到最小的扩充二叉树即为 Huffman树。 § 在Huffman树中,权值大的结点离根最近 7 5 2 4 Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES Huffman编码 Huffman树在数据编码中的应用 设给出一段报文: CAST SAT AT A TASA 字符集合是 { C, A,

DATA STRUCTURES Huffman编码 Huffman树在数据编码中的应用 设给出一段报文: CAST SAT AT A TASA 字符集合是 { C, A, S, T },各个字符出现 的频度(次数)是 W={ 2, 7, 4, 5 }。 若给每个字符以等长编码 A : 00 T : 10 C : 01 S : 11 则总编码长度为: ? ( 2+7+4+5 ) * 2 = 36 Department of Computer Science & Technology, Nanjing University fall 2009

A : 00 T : 10 C : 01 S : 11 0 1

A : 00 T : 10 C : 01 S : 11 0 1 0 7 2 5 A C T 1 4 S ( 2+7+4+5 ) * 2 = 36 最小冗余编码问题 A : 0 T : 10 DATA STRUCTURES C : 110 S : 111 0 7 7*1+5*2+( 2+4 )*3 = 35 1 1 0 5 0 1 2 4 Huffman编码树 Department of Computer Science & Technology, Nanjing University fall 2009

DATA STRUCTURES 利用Huffman树构造最小长度的编码 Huffman编码 例: 各字符出现概率为{ 2/18, 7/18, 4/18, 5/18 } • 化整为 {

DATA STRUCTURES 利用Huffman树构造最小长度的编码 Huffman编码 例: 各字符出现概率为{ 2/18, 7/18, 4/18, 5/18 } • 化整为 { 2, 7, 4, 5 } • 以它们为各叶结点上的权值, 建立Huffman树 • 左分支赋 0,右分支赋 1,得 (变长编码)。 0 7 1 1 0 5 0 1 2 4 总编码长度: Huffman树的带权路径长度WPL Department of Computer Science & Technology, Nanjing University fall 2009