Árbol: definición Árbol (del latín arbor –oris): Planta perenne, de tronco leñoso y elevado, que se ramifica a cierta altura del suelo. (otras, ver Real Academia Española…) Árboles binarios Franco Guidi Polanco Escuela de Ingeniería Industrial Pontificia Universidad Católica de Valparaíso, Chile [email protected] Actualización: 13 de mayo de 2005 Franco Guidi Polanco Árbol: definición (cont.) Árbol: definición (cont.) Árbol: Grafo conexo, no orientado y acíclico. Árbol: Una estructura de datos accesada desde un nodo raíz. Cada nodo es ya sea una hoja o un nodo interno. Un nodo interno tiene uno o más nodos hijos, y se le llama padre de sus nodos hijos. C E A 2 Un árbol es, ya sea: • un conjunto vacío, o • una raíz con cero o más árboles B D H Franco Guidi Polanco 3 Franco Guidi Polanco 4 Hojas y nodos internos Representación de un árbol Una hoja es cualquier nodo que tiene sus hijos vacíos. Un nodo interno es cualquier nodo con al menos un hijo no vacío. subárbol b a b e f h 5 c h d j i l e j i subárbol m k subárbol Franco Guidi Polanco 6 Nodos padres e hijos Las raíces de los subárboles de un árbol son hijos de la raíz del árbol. Existe un arco desde cada nodo a cada uno de sus hijos, y se dice que este nodo es padre de sus hijos. a g d subárbol Representación de un árbol (cont.) f h l Franco Guidi Polanco b g f g Hojas c Nodos internos c d raíz a e k m subárbol de nodo e subárboles de nodo b subárboles de nodo c Franco Guidi Polanco 7 Franco Guidi Polanco 8 Ruta y largo de una ruta Ancestros y descendientes Si n1, n2,... nk es una secuencia de nodos en un árbol, de modo que ni es padre de ni + 1, para 1<=i<=k, entonces esta secuencia se llama ruta desde n1 a nk. El largo de esta ruta es k. a n1 b c d Si existe una ruta desde un nodo A a un nodo B, entonces A es ancestro de B y B es descendiente de A. Luego, todos los nodos de un árbol son descendientes de la raíz del árbol, mientras que la raíz es el ancestro de todos los nodos. n2 e f g n3 h Franco Guidi Polanco 9 Altura Franco Guidi Polanco 10 Niveles La altura de un nodo M de un árbol corresponde al número de nodos en la ruta desde la raíz hasta M. La altura de un árbol corresponde a la altura del nodo más profundo. Todos los nodos de altura d están en el nivel d en el árbol. La raíz está en el nivel 1, y su altura es 1. a Nivel 1 a b Altura del nodo=2 c Nivel 3 Altura del árbol=4 d e f Nivel 4 g Franco Guidi Polanco b Nivel 2 d c e f g h h 11 Franco Guidi Polanco 12 Árboles binarios Representación de un árbol binario (I) Un A.B. está constituido por un conjunto finito de elementos llamados nodos. raíz subárbol izquierdo a Un árbol binario: b no tiene nodos (está vacío); o tiene un nodo llamado raíz, junto con otros dos árboles binarios llamados subárboles derecho e izquierdo de la raíz. d subárbol derecho c e f g h Nota: Una parte importante del material presentado en esta sección fue elaborado por Marcelo Silva F. Franco Guidi Polanco 13 Representación de un árbol binario (II) Franco Guidi Polanco 14 Igualdad de árboles binarios Para ser iguales, dos árboles deben tener tanto la misma estructura, como el mismo contenido. raíz a subárbol derecho b d subárbol izquierdo c e f g a h b Franco Guidi Polanco 15 Franco Guidi Polanco ≠ a b 16 Árboles binarios llenos Árboles binarios completos Un árbol binario lleno es aquel en que cada nodo es un nodo interno con dos hijos no vacíos, o una hoja. a b d Un árbol binario completo tiene una forma restringida, que se obtiene al ser llenado de izquierda a derecha. En un A.B. Completo de altura d, todos los niveles, excepto posiblemente el nivel d están completamente llenos. a c e b f g No es A.B. lleno c e h a f g b Es un A.B. completo pero no es un A.B. lleno h d c e f Es A.B. lleno Franco Guidi Polanco 17 Franco Guidi Polanco 18 Representación de árboles binarios mediante nodos y referencias Número de nodos en un árbol binario El máximo número de nodos en el nivel i de un árbol binario es 2(i-1). El máximo número de nodos en un árbol binario de altura K es 2(K)-1. a b c d e f Franco Guidi Polanco 19 Franco Guidi Polanco 20 Diagrama de clases de un árbol binario Diagrama de objetos de un árbol binario Diagrama de clases árbol binario de enteros: ABB :ABB root:ABBNode ABBNode data:20 1..1 data:int insert(i:int) find(d:Data):boolean delete(i:int) root left setData(i:int) getData():int setLeft(n:ABBNode) getLeft():ABBNode setRight(n:ABBNode) getRight():ABBNode isLeaf():boolean data:2 Franco Guidi Polanco 21 Representación de árboles binarios mediante arreglos c 1 2 3 4 a b c d Franco Guidi Polanco 5 6 7 e f 8 9 10 h 11 12 13 14 data:40 Franco Guidi Polanco 22 Preorden Inorden Postorden f g data:15 :ABBNode Un recorrido es cualquier proceso destinado a visitar los nodos de un árbol binario en un determinado orden. Cualquier recorrido que visite cada nodo exactamente una vez, se denomina una enumeración de los nodos del árbol. Recorridos de enumeración a analizar: a e :ABBNode Recorrido de árboles binarios Si la raíz de un subárbol se almacena en A[i], su hijo izquierdo se almacena en A[2*i], y su hijo derecho en A[2*i+1]. d data:32 data:7 right :ABBNode b :ABBNode :ABBNode 15 16 g h 23 Franco Guidi Polanco 24 Recorrido en Preorden Código para recorrido Preorden Dado un árbol binario: void preorder(BinNode rt) // rt es la raíz del subarbol { if (rt==null) return; // subarbol vacío visit(rt) // hace algo con el nodo preorder(rt.left()); preorder(rt.right()); } 1) Visitar su raíz. 2) Recorrer en preorden su subárbol izquierdo. 3) Recorrer en preorden su subárbol derecho. 1 2 3 Franco Guidi Polanco 25 Ejemplo de recorrido en Preorden 2 b 3 d 26 Recorrido en Inorden Dado un árbol binario: a 1 Franco Guidi Polanco c e 1) Recorrer en inorden su subárbol izquierdo. 2) Visitar su raíz. 3) Recorrer en inorden su subárbol derecho. f g h i j 2 k 1 3 a b d c e f g i j k h Franco Guidi Polanco 27 Franco Guidi Polanco 28 Código para recorrido Inorden Ejemplo de recorrido en Inorden a 2 void inorder(BinNode rt) // rt es la raíz del subarbol { if (rt==null) return; // subarbol vacío inorder(rt.left()); visit(rt) // hace algo con el nodo inorder(rt.right()); } 1 b 3 d c e f g h i j k d b a e c g j i k f h Franco Guidi Polanco 29 Recorrido en Postorden Franco Guidi Polanco 30 Código para recorrido Postorden Dado un árbol binario: void postorder(BinNode rt) // rt es la raíz del subarbol { if (rt==null) return; // subarbol vacío postorder(rt.left()); postorder(rt.right()); visit(rt) // hace algo con el nodo } 1) Recorrer en postorden su subárbol izquierdo. 2) Recorrer en postorden su subárbol derecho. 3) Visitar su raíz. 3 1 Franco Guidi Polanco 2 31 Franco Guidi Polanco 32 Ejemplo de recorrido en Postorden Supongamos que tenemos un conjunto de n elementos que pueden ser ordenados por alguna clave. En un árbol binario de búsqueda (ABB), todos los nodos almacenados en el subárbol izquierdo de un nodo cuyo valor clave es C tienen claves menores que C, mientras que todos los nodos ubicados en el subárbol derecho tienen claves mayores que C. a 3 1 Árbol binario de búsqueda b 2 d c e f g h i j k d b e j k i g hf c a Franco Guidi Polanco 33 Ejemplos de árboles binarios de búsqueda 34 Ingreso de elementos a un ABB a b Franco Guidi Polanco { 10, 5, 7, 15, 14, 12, 18 } { 15, 18, 14, 5, 10, 12, 7 } c 15 c d <c >c e f 10 14 18 No es ABB 5 c Definición de ABB b 15 7 14 18 10 e 12 a 5 d 7 12 f Es ABB Franco Guidi Polanco 35 Franco Guidi Polanco 36 ABB de referencia Ingreso de elementos a un ABB (cont.) ABB insert(e:Element) find(key:int):Element delete(i:int):Element Element ABBNode 1 setData(e:Element) root getData():Element left setLeft(n:ABBNode) getLeft():ABBNode setRight(n:ABBNode) getRight():ABBNode isLeaf():boolean 1 {interface} private BinNode insert (BinNode rt, Element val) { if (rt == null) return new BinNode(val); Element it = (Element)rt.element(); if (it.key() > val.key()) rt.setLeft(insert(rt.left(), val)); else rt.setRight(insert(rt.right(), val)); return rt; } data getKey():int right Franco Guidi Polanco 37 Franco Guidi Polanco Características del ingreso de elementos a un ABB 38 Recorrido Inorden en ABB Los elementos agregados a un ABB siempre son incorporados inicialmente como hojas. Un conjunto de elementos dado puede generar diversos ABB, dependiendo del orden en que son ingresados. 15 10 14 5 15 7 14 5 18 10 12 5 Franco Guidi Polanco 39 7 Franco Guidi Polanco 18 10 12 14 15 18 7 5 12 7 10 12 14 15 18 40 Características del recorrido Inorden de un ABB Búsqueda en ABB Para hallar un elemento con clave C, en un árbol A: Si bien existen muchos ABBs posibles para un mismo conjunto de elementos, el recorrido Inorden de todos estos árboles siempre entrega el conjunto ordenado de menor a mayor. Franco Guidi Polanco Si la raíz del árbol A almacena C, la búsqueda termina exitosamente. Si C es menor que el valor de la raíz de A, buscar en el subárbol izquierdo. Si C es mayor que el valor de la raíz, buscar en el subárbol derecho. La búsqueda termina al hallar el valor C, o al pretender buscar en un subárbol vacío. 41 Búsqueda en ABB (cont.) Franco Guidi Polanco 42 Ejemplo de búsqueda en ABB 10 10 Elem find(BinNode rt, int key) { if (rt == null) return null; Element it = (Element)rt.element(); if ((int)it.key() > key) return find(rt.left(), key); else if (it.key() == key) return it; else return find(rt.right(), key); } Franco Guidi Polanco 5 5 15 7 14 18 12 Buscar 12 Búsqueda exitosa 43 Franco Guidi Polanco 15 7 14 18 12 Buscar 16 Búsqueda infructuosa 44 Eliminar nodo que es una hoja o tiene a lo más un hijo Eliminación de elementos de un ABB Se pueden presentar tres casos: El elemento no existe. El elemento es una hoja o tiene a lo más un hijo. El elemento tiene dos hijos. 10 10 5 15 7 14 7 18 12 Franco Guidi Polanco 45 Ejemplo eliminación de nodo con dos hijos 10 15 7 14 5 18 16 18 17 17 Franco Guidi Polanco 14 18 12 Franco Guidi Polanco 46 1. Hallar el nodo que contiene el menor de los elementos mayores del nodo a eliminar (el elemento más a la izquierda de su subárbol derecho) 2. Reemplazar los datos del nodo eliminar con los del nodo hallado. 3. Eliminar el nodo hallado, que tiene a lo más un hijo, con el procedimiento descrito previamente. 16 7 14 Eliminar nodo con dos hijos 10 5 15 El menor de los elementos mayores (Nodo más a la izquierda del subárbol derecho) 47 Franco Guidi Polanco 48 Importancia de una estructura balanceada en los ABB Utilidad de los árboles binarios de búsqueda La estructura de un ABB es importante al momento de realizar búsquedas en él. Al buscar, el ABB permite descartar a priori un subconjunto de elementos, en forma análoga a la búsqueda binaria en arreglos ordenados. El ABB presenta además la ventaja de poder ser implementado con punteros (estructura dinámica). La incorporación y eliminación de elementos al ABB es mas rápida que en arreglos ordenados. 18 10 15 5 3 15 7 14 14 En el peor de los casos se hacen 3 iteraciones para una búsqueda. Franco Guidi Polanco 49 Franco Guidi Polanco 10 18 7 5 3 En el peor de los casos se hacen 7 iteraciones para una búsqueda. 50