Arboles Binarios– Parte 2 - Ciencias Computacionales
Transcription
Arboles Binarios– Parte 2 - Ciencias Computacionales
Propedéutico de Programación Coordinación de Ciencias Computacionales Semana 6, Primera Parte Dra. Pilar Gómez Gil http://ccc.inaoep.mx/~pgomez/cursos/programacion/ Versión 1.2 08.07.08 Chapter 8 Binary Search Trees Continuación… Tomado de: Dale, N. Weems, C++ Plus Data Structures 4th. Ed. 2007 Instructor material, © Jones & Barlett Publishers Tree Recursion CountNodes Version 1 if (Left(tree) is NULL) AND (Right(tree) is NULL) return 1 else return CountNodes(Left(tree)) + CountNodes(Right(tree)) + 1 What happens when Left(tree) is NULL? Tomado de: Dale, N. Weems, C++ Plus Data Structures 4th. Ed. 2007 Instructor material, © Jones & Barlett Publishers Tree Recursion CountNodes Version 2 if (Left(tree) is NULL) AND (Right(tree) is NULL) return 1 else if Left(tree) is NULL return CountNodes(Right(tree)) + 1 else if Right(tree) is NULL return CountNodes(Left(tree)) + 1 else return CountNodes(Left(tree)) + CountNodes(Right(tree)) + 1 What happens when the initial tree is NULL? Tomado de: Dale, N. Weems, C++ Plus Data Structures 4th. Ed. 2007 Instructor material, © Jones & Barlett Publishers Tree Recursion CountNodes Version 3 if tree is NULL return 0 else if (Left(tree) is NULL) AND (Right(tree) is NULL) return 1 else if Left(tree) is NULL return CountNodes(Right(tree)) + 1 else if Right(tree) is NULL return CountNodes(Left(tree)) + 1 else return CountNodes(Left(tree)) + CountNodes(Right(tree)) + 1 Can we simplify this algorithm? Tomado de: Dale, N. Weems, C++ Plus Data Structures 4th. Ed. 2007 Instructor material, © Jones & Barlett Publishers Tree Recursion CountNodes Version 4 if tree is NULL return 0 else return CountNodes(Left(tree)) + CountNodes(Right(tree)) + 1 Is that all there is? Tomado de: Dale, N. Weems, C++ Plus Data Structures 4th. Ed. 2007 Instructor material, © Jones & Barlett Publishers // Implementation of Final Version int CountNodes(TreeNode* tree); // Pototype int TreeType::LengthIs() const // Class member function { return CountNodes(root); } int CountNodes(TreeNode* tree) // Recursive function that counts the nodes { if (tree == NULL) return 0; else return CountNodes(tree->left) + CountNodes(tree->right) + 1; Tomado de: Dale, N. Weems, C++ Plus Data Structures 4th. Ed. } 2007 Instructor material, © Jones & Barlett Publishers Retrieval Operation Tomado de: Dale, N. Weems, C++ Plus Data Structures 4th. Ed. 2007 Instructor material, © Jones & Barlett Publishers Retrieval Operation void TreeType::RetrieveItem(ItemType& item, bool& found) { Retrieve(root, item, found); } void Retrieve(TreeNode* tree, ItemType& item, bool& found) { if (tree == NULL) found = false; else if (item < tree->info) Retrieve(tree->left, item, found); Tomado de: Dale, N. Weems, C++ Plus Data Structures 4th. Ed. 2007 Instructor material, © Jones & Barlett Publishers Retrieval Operation, cont. else if (item > tree->info) Retrieve(tree->right, item, found); else { item = tree->info; found = true; } } Tomado de: Dale, N. Weems, C++ Plus Data Structures 4th. Ed. 2007 Instructor material, © Jones & Barlett Publishers The Insert Operation • A new node is always inserted into its appropriate position in the tree as a leaf. Tomado de: Dale, N. Weems, C++ Plus Data Structures 4th. Ed. 2007 Instructor material, © Jones & Barlett Publishers Insertions into a Binary Search Tree Tomado de: Dale, N. Weems, C++ Plus Data Structures 4th. Ed. 2007 Instructor material, © Jones & Barlett Publishers The recursive InsertItem operation Por ejemplo, insertando11… Tomado de: Dale, N. Weems, C++ Plus Data Structures 4th. Ed. 2007 Instructor material, © Jones & Barlett Publishers The tree parameter is a pointer within the tree Tomado de: Dale, N. Weems, C++ Plus Data Structures 4th. Ed. 2007 Instructor material, © Jones & Barlett Publishers Recursive Insert void Insert(TreeNode*& tree, ItemType item) { if (tree == NULL) {// Insertion place found. tree = new TreeNode; tree->right = NULL; tree->left = NULL; tree->info = item; } else if (item < tree->info) Insert(tree->left, item); else Insert(tree->right, item); } Tomado de: Dale, N. Weems, C++ Plus Data Structures 4th. Ed. 2007 Instructor material, © Jones & Barlett Publishers Eliminando un Nodo • Hay 3 posibles casos: 1. Que el nodo a eliminarse no tenga ningún hijo 2. Que el nodo a eliminarse tenga un hijo 3. Que el nodo a eliminarse tenga dos hijos Deleting a Leaf Node Caso 1 La eliminación es simplemente limpiar memoria Tomado de: Dale, N. Weems, C++ Plus Data Structures 4th. Ed. 2007 Instructor material, © Jones & Barlett Publishers Deleting a Node with One Child Caso 2 La eliminación consiste en que el hijo toma el lugar del padre… Tomado de: Dale, N. Weems, C++ Plus Data Structures 4th. Ed. 2007 Instructor material, © Jones & Barlett Publishers Deleting a Node with Two Children Caso 3 Hay que determinar quien toma el lugar del padre sin que se afecte el árbol… Q Tomado de: Dale, N. Weems, C++ Plus Data Structures 4th. Ed. 2007 Instructor material, © Jones & Barlett Publishers Para el caso 3 • El lugar del padre eliminándose, lo puede tomar su predecesor inmediato o su sucesor inmediato. • En éste caso se utiliza al predecesor, el cual es el valor mas grande en el subárbol izquierdo del elemento eliminándose, esto es, el nodo que está mas hacia la derecha en el subárbol izquierdo Tomado de: Dale, N. Weems, C++ Plus Data Structures 4th. Ed. 2007 Instructor material, © Jones & Barlett Publishers DeleteNode Algorithm if (Left(tree) is NULL) AND (Right(tree) is NULL) Set tree to NULL else if Left(tree) is NULL Set tree to Right(tree) else if Right(tree) is NULL Set tree to Left(tree) else Find predecessor Set Info(tree) to Info(predecessor) Delete predecessor Tomado de: Dale, N. Weems, C++ Plus Data Structures 4th. Ed. 2007 Instructor material, © Jones & Barlett Publishers Code for DeleteNode void DeleteNode(TreeNode*& tree) { ItemType data; TreeNode* tempPtr; tempPtr = tree; if (tree->left == NULL) { tree = tree->right; delete tempPtr; } else if (tree->right == NULL){ tree = tree->left; delete tempPtr;} els{ GetPredecessor(tree->left, data); tree->info = data; Delete(tree->left, data);} Tomado de: Dale, N. Weems, } C++ Plus Data Structures • Pero primero hay que encontrar el nodo a eliminarse… recordando: DeleteItem(itemType item) • Función: Borra el elemento cuya llave coincide con la llave de item • Precondición: La llave de item se inicializó. Uno y solo uno de los elementos en el árbol tiene una llave que coincide con la de item • Postcondición: Ningún elemento en el árbol tiene una llave que coincide con la de item Tomado de: Dale, N. Weems, C++ Plus Data Structures 4th. Ed. 2007 Instructor material, © Jones & Barlett Publishers Definition of Recursive Delete Definition: Size: Removes item from tree The number of nodes in the path from the root to the node to be deleted. Base Case: If item's key matches key in Info(tree), delete node pointed to by tree. General Case: If item < Info(tree), Delete(Left(tree), item); else Delete(Right(tree), item). Tomado de: Dale, N. Weems, C++ Plus Data Structures 4th. Ed. 2007 Instructor material, © Jones & Barlett Publishers Código void TreeType::DeleteItem(ItemType item) // Calls recursive function Delete to delete item from tree. { Delete(root, item); } Tomado de: Dale, N. Weems, C++ Plus Data Structures 4th. © Jones & Barlett Publishers Code for Recursive Delete void Delete(TreeNode*& tree, ItemType item) { if (item < tree->info) Delete(tree->left, item); else if (item > tree->info) Delete(tree->right, item); else DeleteNode(tree); // Node found } Tomado de: Dale, N. Weems, C++ Plus Data Structures 4th. Ed. 2007 Instructor material, © Jones & Barlett Publishers Code for GetPredecessor void GetPredecessor(TreeNode* tree, ItemType& data) { while (tree->right != NULL) tree = tree->right; data = tree->info; } Tomado de: Dale, N. Weems, C++ Plus Data Structures 4th. Ed. 2007 Instructor material, © Jones & Barlett Publishers Printing all the Nodes in Order Tomado de: Dale, N. Weems, C++ Plus Data Structures 4th. Ed. 2007 Instructor material, © Jones & Barlett Publishers Function Print Definition: Prints the items in the binary search tree in order from smallest to largest. Size: The number of nodes in the tree whose root is tree Base Case: If tree = NULL, do nothing. General Case: Traverse the left subtree in order. Then print Info(tree). Then traverse the right subtree in order. Tomado de: Dale, N. Weems, C++ Plus Data Structures 4th. Ed. 2007 Instructor material, © Jones & Barlett Publishers Code for Recursive InOrder Print void PrintTree(TreeNode* tree, std::ofstream& outFile) { if (tree != NULL) { PrintTree(tree->left, outFile); outFile << tree->info; PrintTree(tree->right, outFile); } } Tomado de: Dale, N. Weems, C++ Plus Data Structures 4th. Ed. 2007 Instructor material, © Jones & Barlett Publishers Destructor void Destroy(TreeNode*& tree); TreeType::~TreeType() { Destroy(root); } void Destroy(TreeNode*& tree) { if (tree != NULL) { Destroy(tree->left); Destroy(tree->right); delete tree; } } Tomado de: Dale, N. Weems, C++ Plus Data Structures 4th. Ed. 2007 Instructor material, © Jones & Barlett Publishers Algorithm for Copying a Tree if (originalTree is NULL) Set copy to NULL else Set Info(copy) to Info(originalTree) Set Left(copy) to Left(originalTree) Set Right(copy) to Right(originalTree) Tomado de: Dale, N. Weems, C++ Plus Data Structures 4th. Ed. 2007 Instructor material, © Jones & Barlett Publishers Code for CopyTree void CopyTree(TreeNode*& copy, const TreeNode* originalTree) { if (originalTree == NULL) copy = NULL; else { copy = new TreeNode; copy->info = originalTree->info; CopyTree(copy->left, originalTree->left); CopyTree(copy->right, originalTree->right); } } Tomado de: Dale, N. Weems, C++ Plus Data Structures 4th. Ed. 2007 Instructor material, © Jones & Barlett Publishers Recorrido recursivo de árboles binarios - Preorder Raíz Árbol Izquierdo Árbol Derecho - Inorder Árbol Izquierdo Raíz Árbol Derecho - Postorder Árbol Izquierdo Árbol Derecho Raíz Tomado de: Dale, N. Weems, C++ Plus Data Structures 4th. Ed. 2007 Instructor material, © Jones & Barlett Publishers Inorder(tree) if tree is not NULL Inorder(Left(tree)) Visit Info(tree) Inorder(Right(tree)) To print in alphabetical order Tomado de: Dale, N. Weems, C++ Plus Data Structures 4th. Ed. 2007 Instructor material, © Jones & Barlett Publishers Postorder(tree) if tree is not NULL Postorder(Left(tree)) Postorder(Right(tree)) Visit Info(tree) Tomado de: Dale, N. Weems, C++ Plus Data Structures 4th. Ed. 2007 Instructor material, © Jones & Barlett Publishers Preorder(tree) if tree is not NULL Visit Info(tree) Preorder(Left(tree)) Preorder(Right(tree)) Tomado de: Dale, N. Weems, C++ Plus Data Structures 4th. Ed. 2007 Instructor material, © Jones & Barlett Publishers Three Tree Traversals Tomado de: Dale, N. Weems, C++ Plus Data Structures 4th. Ed. 2007 Instructor material, © Jones & Barlett Publishers Our Iteration Approach • The client program passes the ResetTree and GetNextItem functions a parameter indicating which of the three traversals to use • ResetTree generates a queues of node contents in the indicated order • GetNextItem processes the node contents from the appropriate queue: inQue, preQue, postQue. Tomado de: Dale, N. Weems, C++ Plus Data Structures 4th. Ed. 2007 Instructor material, © Jones & Barlett Publishers Code for ResetTree void TreeType::ResetTree(OrderType order) // Calls function to create a queue of the tree // elements in the desired order. { switch (order) { case PRE_ORDER : PreOrder(root, preQue); break; case IN_ORDER : InOrder(root, inQue); break; case POST_ORDER: PostOrder(root, postQue); break; } } Tomado de: Dale, N. Weems, C++ Plus Data Structures 4th. Ed. 2007 Instructor material, © Jones & Barlett Publishers Code for GetNextItem void TreeType::GetNextItem(ItemType& item, OrderType order,bool& finished) { finished = false; switch (order) { case PRE_ORDER : preQue.Dequeue(item); if (preQue.IsEmpty()) finished = true; break; case IN_ORDER : inQue.Dequeue(item); if (inQue.IsEmpty()) finished = true; break; case POST_ORDER: postQue.Dequeue(item); if (postQue.IsEmpty()) finished = true; break; } } Tomado de: Dale, N. Weems, C++ Plus Data Structures 4th. Ed. 2007 Instructor material, © Jones & Barlett Publishers • Ver – TreeType.h – TreeType.cpp