// ------------------------------------------------------------------------------ // Funcao exclude // ------------------------------------------------------------------------------ nodo * exclude (nodo * raiz, element * x) { nodo * temp, * filho; // se a arvore estiver vazia if (raiz == NULL){ printf("Erro nodo nao encontrado"); return NULL; } else if (x->valor < raiz->chave->valor){ // esquerda raiz->esq = exclude(raiz->esq, x); raiz = balanceamento(raiz); } else if ( x->valor > raiz->chave->valor){ // direita raiz->dir = exclude(raiz->dir, x); raiz = balanceamento(raiz); } else if (raiz->esq && raiz->dir) { // se tiver 2 filhos temp = find_min(raiz->dir); raiz->chave->valor = temp->chave->valor; raiz->dir = exclude(raiz->dir, raiz->chave); } else { // filho unico temp = raiz; if (raiz->esq == NULL) // so tem filho a direita filho = raiz->dir; if (raiz->dir == NULL){ // so tem filho a esquerda filho = raiz->esq; } free(temp); return filho; } return raiz; }
// ------------------------------------------------------------------------------ // Funcao insert // ------------------------------------------------------------------------------ nodo * insert (nodo * raiz, element * x) { if (raiz != NULL){ // se a raiz for diferente de null entra na recursao // se for igual if (x->valor == raiz->chave->valor){ return raiz; } if (x->valor < raiz->chave->valor){ raiz->esq = insert(raiz->esq, x); } else { if (x->valor > raiz->chave->valor){ raiz->dir = insert(raiz->dir, x); } } raiz = balanceamento(raiz); } else { // senao aloca o nodo e o valor if(!(raiz = malloc(sizeof(nodo)))){ printf("\n"); printf("Erro no malloc do nodo."); printf("\n"); return NULL; } raiz->chave = x; raiz->dir = NULL; raiz->esq = NULL; } return raiz; }
/* Função que calcula o fator de balanceamento da arvore */ int balanceamento(PPNo raiz) { int alt_e, alt_d; if(*raiz) { alt_e = balanceamento(&(*raiz)->esq); /* funcao balanceamento retorna a altura total da sub-arvore esquerda */ alt_d = balanceamento(&(*raiz)->dir); /* mesma coisa para a sub-arvore direita */ (*raiz)->balanc = alt_e - alt_d; /* calcula o fator de balanceamento do nó usando as alturas das sub-arvores como parametro */ if((*raiz)->balanc < -1) { /* se o nó esta desbalanceado para direita */ if(((*raiz)->dir)->balanc <= 0) rotacionaDir(raiz); /* se o nó filho da direita esta balanceado ou desbalanceado para direita, entao faz uma rotação simples para a direita*/ else rotacionaDirEsq(raiz); /* se não, faz uma rotação dupla direita-esquerda */ alt_e = balanceamento(&(*raiz)->esq); /* recalcula os balanceamentos das sub-arvores */ alt_d = balanceamento(&(*raiz)->dir); (*raiz)->balanc = alt_e - alt_d; } if((*raiz)->balanc > 1) { /* se o nó esta desbalanceado para a esquerda */ if(((*raiz)->esq)->balanc >= 0) rotacionaEsq(raiz); /* se o nó filho da esquerda esta balanceado ou desbalanceado para esquerda, entao faz uma rotação para esquerda */ else rotacionaEsqDir(raiz); /* se não, faz uma rotação dupla esquerda-direita */ alt_d = balanceamento(&(*raiz)->dir); /* recalcula os balanceamentos das sub-arvores */ alt_e = balanceamento(&(*raiz)->esq); (*raiz)->balanc = alt_e - alt_d; } /* retorna a altura do nó */ if(alt_e > alt_d) return alt_e +1; else return alt_d +1; }else { return 0; /* se o nó nao existe, entao altura = 0 */ } }
/* Insere um novo nó */ void insereNo(PPNo raiz,int chave) { PNo novo, pai; novo = novoNo(chave); /* aloca memória para o novo nó */ pai = busca(*raiz,chave,NULL); /* busca endereço do pai do novo nó */ if(pai) { /* se o pai existe, adiciona novo nó como filho dele */ if(pai->chave == chave) { /* se a chave a ser inserida ja existe, mostra aviso na tela */ gotoxy(1,1); printf("Chave ja existe!\n"); }else { if(chave > pai->chave) pai->dir = novo; else pai->esq = novo; } } balanceamento(raiz); /* recalcula balanceamento da arvore */ }