Estructuras de datos Heap (montículo)
description
Transcript of Estructuras de datos Heap (montículo)
Estructuras de datos Heap (montículo)
• Un árbol completo, es aquel en el que todos los niveles, con excepción del último, tiene sus nodos completos. Un arbol perfectamente equilibrado hasta el penultimo nivel, y en el ultimo nivel los nodos se encuentran agrupados a la izquierda .
• Un Heap es un árbol binario completo a izquierda, que permite implementar una cola con prioridad, y donde los elementos se almacenan cumpliendo la propiedad de que la clave de un nodo siempre es mayor (o menor) que la clave de cualquiera de sus hijos. Lo que nos asegura que la raíz del árbol, en un Heap, siempre es el elemento mayor (o menor) de la estructura.
• Arbol binario lleno • Arbol binario completo
CB
D F G H
A
32
4 5 6 7
9 10
1
8
Ejemplos
Monticulo o Heap• El acceso a los
elementos del Heap en un arreglo, se hace a través de algunas operaciones aritméticas básicas:
Left(i) : return 2*i .- Obtiene el hijo izquierdo del elemento i.
Right(i) : return 2*i +1 .- Obtiene el hijo derecho del elemento i.
Parent(i): return floor(i/2) .- Obtiene el padre del elemento i.
Crear un arbol binario• Carga(nodo)1.- Leer informacion(info)2.- Hacer nodo^.info=info3.- Escribir “Existe nodo por la izquierda?”4.- Leer repuesta5.- Si respuesta es afirmativa
entoncescrea(otro)hacer nodo^.izq=otroregresar a carga(nodo^.izq)//llamada recursiva
sinohacer nodo^.izq=Nil
6.- fin del paso 57.- 3.- Escribir “Existe nodo por la derecha?”8.- Leer repuesta9.- Si respuesta es afirmativa
entoncescrea(otro)hacer nodo^.der=otroregresar a carga(nodo^.der)//llamada recursiva
sinohacer nodo^.der=Nil
10.- fin del paso 9
Recorridos de arboles
• Recorrido en preorden1.-Visita la raiz
2.- recorre el subarbol izquierdo
3.- recorre el subarbol derecho
• Recorrido en inorden1.- recorre el subarbol izquierdo
2.- Visita la raiz
3.- recorre el subarbol derecho
• Recorrido en postorden1.- recorre el subarbol izquierdo
2.- recorre el subarbol derecho
3.- Visita la raiz
Algoritmo para recorrerlo en Preorden
• Preorden(nodo)
1.- Si nodo <>nil entonces
visita el nodo(escribir la info del nodo)
Regresa preorden(nodo^.izq)
Regresa preorden(nodo^.der)
2.- fin del paso 1
Algoritmo para recorrerlo en Inorden
• Inorden(nodo)
1.- Si nodo <>nil entonces
Regresa inorden(nodo^.izq)
visita el nodo(escribir la info del nodo) Regresa inorden(nodo^.der)
2.- fin del paso 1
Algoritmo para recorrerlo en Postorden
• Postorden(nodo)
1.- Si nodo <>nil entonces
Regresa Postorden(nodo^.izq)
Regresa postorden(nodo^.der)
visita el nodo(escribir la info del nodo)2.- fin del paso 1
Ejemplos:
• Carga los nodos: 95-96-13-73-14-18-29
• RecorridoPreorden95-96-13-73-14-18-29Inorden13-96-73-95-18-14-29Postorden 13-73-96-18-29-14-95
1496
13 73 18 29
95
Arboles binarios de busqueda
• Para todo nodo T del arbol debe cumplirse que todos los valores de los nodos del subarbol izquierdo de T seran menores al valor del nodo T y todos los valores de los nodos del subarbor derecho de T deben ser mayores. Si los valores se repiten solo se inserta una vez.
Insercion en un arbol binario de busqueda• Insercion(nodo,info)1.- Si nodo<>Nilentonces1.1 Si info<nodo^.info
entoncesinsercion(nodo^.izq,info)sino1.1.1 Si info>nodo^.info entonces insercion(nodo^.der,info) sino Escribir “informacion ya existente”1.1.2 fin de 1.1.1
1.2 fin de 1.1sino
crea(otro)otro^.izq=otro^.der=Nilotro^.info=info,nodo=otro.
2.- fin de 1
95
16 104
13 73 100 129
Insertar:95,16,104,13,100,129,73
Recorridos en un arbol binario de busqueda
• Preorden: 95-16-13-73-104-100-129
• Postorden13-73-16-100-129-104-95
• Inorden:13-16-73-95-100-104-129
95
16 104
13 73 100 129
Busqueda de un elemento en un arbol binario de busqueda(recursivo)
• Busqueda(nodo,info)1.- Si nodo<>Nilentonces1.1 Si info<nodo^.info
entoncesBusqueda(nodo^.izq,info)
sino1.1.1 Si info>nodo^.info
entoncesBusqueda(nodo^.der,info)
sinoEscribir “El dato esta en el arbol”
1.1.2 fin del paso 1.1.11.2 fin del paso 1.1sino
Escribir “El dato no esta en el arbol”
Ejemplo
• En que lugar quedaria insertado el numero 20
• Inserta 99• Inserta 84
9750
12 73 96
200
100
95
Eliminar un nodo• Hay que eliminar un nodo si violar los principios que
definen un arbol binario de busqueda.
1.- Si el nodo es terminal u hoja, simplemente se suprime
2.- Si solo tiene un solo descendiente, entonces tiene que sustituirse por ese descendiente
3.- Si tiene dos descendientes, entonces se tiene que sustituir por el nodo que se encuentra mas a la derecha en el subarbol izquierdo o mas a la izquierda en el subarbol derecho.
Pero antes de eliminarlo se tiene que encontrar.
Para eliminar podemos seleccionar el mas grande del subarbol izquierdo o el mas pequeño del subarbol derecho del nodo a eliminar
Algoritmo de eliminacionElimina(int k,int e) //elimina el elemento k y guarda el valor en e{ nodoarbol *p=root,*pp=NULL; while(p && p->dato!=k)//este recorrido busca el nodo, en pp se
guada el padre { pp=p; //del que queremos borrar y en p el nodo
a borrar if(k<p->dato) p=p->izq; else p=p->der; }If(!p) cout<<“No se encuntra el dato”;//si no encontro a kelse {e=p->dato;
If(p->izq &&p->der) //si tiene dos hijos, encuentra el mas grande del subarbol izquierdo{nodoarbol *s=p->izq,*ps=p; //izquierdo de pwhile(s->der)
{ ps=s;s=s->izq;} //se mueve al mas grande
p->dato=s->dato; //copia el dato del mas grande a pp=s;pp=ps;}
Continuacion….//p tiene por lo menos un hijo, lo guarda en cnodoarbol *c; //p tiene por lo menos un subarbolIf(p->izq) c=p->izq; else c=p->der;If(p==root) root=c;else { //identificar si p es el hijo izquierdo o derecho de ppIf(p==pp->izq) pp->izq=c;else pp->der=c;}delete p;} //fin del else de que lo encontro