Árboles Binarios de Búsqueda (ABB) en C++: Implementación y Operaciones

Enviado por Programa Chuletas y clasificado en Informática y Telecomunicaciones

Escrito el en español con un tamaño de 5,34 KB

Contar el Número de Nodos en un ABB

El siguiente código en C++ muestra cómo contar el número de nodos en un árbol binario de búsqueda (ABB).


template<class DATO>
const int ABB<DATO>::NumeroNodos()
{
    contador = 0;
    auxContador(raiz); // Función auxiliar
    return contador;
}

La función NumeroNodos utiliza una función auxiliar recursiva, auxContador, para realizar el conteo.


template<class DATO>
void ABB<DATO>::auxContador(Nodo<DATO> *nodo)
{
    contador++;  // Otro nodo
    // Continuar recorrido
    if(nodo->izquierdo) auxContador(nodo->izquierdo);
    if(nodo->derecho)  auxContador(nodo->derecho);
}

La función auxContador recorre el árbol en preorden, incrementando el contador por cada nodo visitado.

Calcular la Altura de un ABB

El siguiente código calcula la altura de un ABB, que se define como la altura de su nodo de mayor altura.


template<class DATO>
const int ABB<DATO>::AlturaArbol()
{
    altura = 0;
    auxAltura(raiz, 0); // Función auxiliar
    return altura;
}

La función AlturaArbol utiliza una función auxiliar recursiva, auxAltura, para calcular la altura.


template<class DATO>
void ABB<DATO>::auxAltura(Nodo<DATO> *nodo, int a)
{
    // Recorrido postorden
    if(nodo->izquierdo) auxAltura(nodo->izquierdo, a+1);
    if(nodo->derecho)  auxAltura(nodo->derecho, a+1);
    // Proceso, si es un nodo hoja, y su altura es mayor que la actual del
    // árbol, actualizamos la altura actual del árbol
    if(EsHoja(nodo) && a > altura) altura = a;
}

La función auxAltura recorre el árbol en postorden, actualizando la altura solo en los nodos hoja cuya altura sea mayor que la altura actual del árbol.

Insertar un Dato en un ABB

El siguiente código muestra cómo insertar un nuevo dato en un ABB.


template<class DATO>
void ABB<DATO>::Insertar(const DATO dat)
{
    Nodo<DATO> *padre = NULL;
    actual = raiz;
    // Buscar el dato en el árbol, manteniendo un puntero al nodo padre
    while(!Vacio(actual) && dat != actual->dato) {
        padre = actual;
        if(dat > actual->dato) actual = actual->derecho;
        else if(dat < actual->dato) actual = actual->izquierdo;
    }
    // Si el dato ya existe, no se hace nada
    if(!Vacio(actual)) return;
    // Si el árbol está vacío, el nuevo nodo será la raíz
    if(Vacio(padre)) raiz = new Nodo<DATO>(dat);
    // Si el dato es menor que el padre, se inserta a la izquierda
    else if(dat < padre->dato) padre->izquierdo = new Nodo<DATO>(dat);
    // Si el dato es mayor que el padre, se inserta a la derecha
    else if(dat > padre->dato) padre->derecho = new Nodo<DATO>(dat);
}

La función Insertar busca la posición correcta para el nuevo dato y lo inserta como un nuevo nodo hoja.

Eliminar un Elemento de un ABB

El siguiente código muestra cómo eliminar un elemento de un ABB.


template<class DATO>
void ABB<DATO>::Borrar(const DATO dat)
{
    Nodo<DATO> *padre = NULL;
    Nodo<DATO> *nodo;
    DATO aux;
    actual = raiz;
    // Buscar el dato en el árbol
    while(!Vacio(actual)) {
        if(dat == actual->dato) { // Si el valor está en el nodo actual
            if(EsHoja(actual)) { // Y si además es un nodo hoja: lo borramos
                if(padre) { // Si tiene padre (no es el nodo raiz)
                    if(padre->derecho == actual) padre->derecho = NULL;
                    else if(padre->izquierdo == actual) padre->izquierdo = NULL;
                }
                delete actual; // Borrar el nodo
                actual = NULL;
                return;
            } else { // Si el valor está en el nodo actual, pero no es hoja
                padre = actual;
                // Buscar el nodo que reemplazará al actual
                if(actual->derecho) {
                    nodo = actual->derecho;
                    while(nodo->izquierdo) {
                        padre = nodo;
                        nodo = nodo->izquierdo;
                    }
                } else {
                    nodo = actual->izquierdo;
                    while(nodo->derecho) {
                        padre = nodo;
                        nodo = nodo->derecho;
                    }
                }
                // Intercambiar los valores
                aux = actual->dato;
                actual->dato = nodo->dato;
                nodo->dato = aux;
                actual = nodo;
            }
        } else { // Todavía no hemos encontrado el valor, seguir buscándolo
            padre = actual;
            if(dat > actual->dato) actual = actual->derecho;
            else if(dat < actual->dato) actual = actual->izquierdo;
        }
    }
}

La función Borrar busca el nodo a eliminar y lo elimina, manteniendo la estructura del ABB. Se consideran tres casos: eliminar un nodo hoja, eliminar un nodo con un hijo y eliminar un nodo con dos hijos.

Entradas relacionadas: