miguel747 icon

Projeto3ED (proposta)

miguel747 | PRO | 10/23/11 05:01:43 AM UTC | 0 ⭐ | 182 👁️ | Never ⏰ | []
C |

5.07 KB

|

None

|

0 👍

/

0 👎

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#define max 100
 
//Estrutura para armazenar o alfabeto para algoritmo e montar a arvore binaria
typedef struct arv{
    char c;
    int freq;
    int isleft;
    int codigo[10];
    struct arv *prox;
    struct arv *esq;
    struct arv *dir;
}Arv;
//Estrutura da tabela contendo as inforacoes dos cohdigos
typedef struct tabela{
    int codigo[20];
    char a;
}Tabela;
//cria uma lista de arvores com cabeça
Arv* cria_lst(){
    Arv* q = (Arv*)malloc(sizeof(Arv));
    q->c='\n';
    q->freq=max+1;
    q->esq = q->dir = NULL;
    q->prox = NULL;
    return q;
}
//insere as folhas na lista
Arv* lst_insereF(char a, int f, Arv* lis){ 
    Arv* t = (Arv*)malloc(sizeof(Arv));
    t->c = a;
    t->freq = f;
    t->prox = lis->prox;
    lis->prox = t;
    t->esq = t->dir = NULL;
    return lis;
}
//insere subarvores na lista
Arv* lst_insereA(Arv* a, Arv* lis){
    a->prox = lis->prox;
    lis->prox = a;
    return lis;
}
//imprime a arvore
void arv_imprime(Arv* a){ 
    if(!arv_vazia(a)){
        printf("(");
        printf("%c(%d)", a->c, a->isleft);
        
        if(a->esq==NULL)
            printf("()");
        if(a->dir==NULL)
            printf("()");
        arv_imprime(a->esq);
        
        
        arv_imprime(a->dir);
        printf(")");
    }
}
//cria uma subarvore correpondente a 'nao-folha' 
Arv* cria_arv(Arv *sae,Arv *sad){
    Arv* q = (Arv*)malloc(sizeof(Arv));
    q->c = '*';
    q->freq = sae->freq + sad->freq;
    
    q->esq = sae;
    q->dir = sad;
    
    return q;
}
//verifica se a lista com cabeca esta vazia
int vazia(Arv *lis){
    return (lis->prox==NULL);
}
//retira o menor elemento da lista criada com cada celula sendo uma arvore
Arv* retira_menor(Arv* lis){
    Arv *q=lis->prox, *menor = lis->prox, *ant=NULL;
    
    while(q->prox!=NULL){//ponteiro 'menor' pecorre a lista das arvores primarias
        if(menor->freq>q->prox->freq){
            menor = q->prox;
            ant = q;
        }
        q=q->prox;
    }
    
    if(menor==lis->prox){
        
        lis->prox=lis->prox->prox;
        
        return menor;
        
    }
    
    ant->prox = menor->prox;
    menor->prox=NULL;
    return menor;
    
}
//conta a frequencia do caracter digitado pelo usuario
Arv* contafreq(char *m,char a,Arv *lis){
    int i, freq=0;          
    if(a=='\n')
        return lis;
    for(i=0;i<=strlen(m);i++){
        if(m[i]==a){
            freq++;
            m[i]='\n';
        }
    }
    lis = lst_insereF(a,freq,lis);
    return lis;
}
//imprime a lista dos caracteres e suas respecitivas frequencias
void lst_imprime(Arv* lis){
    Arv *p;
    for(p = lis;p!=NULL; p=p->prox)
        printf("info = %c(%d)\n", p->c,p->freq) ;
}
//quantidade de sub arvores na lista de sub arvores
int Nos(Arv* lis){
    int i=0;
    while(lis!=NULL){
        i++;
        lis=lis->prox;
    }
    return i;
}
//insere no campo isleft caso a arvore sej colocada a direita ou a esqueda da subfolha
void Arv_left(Arv* A,Arv* sae, Arv *sad){
    if(A!=NULL&&A->esq!=NULL&&A->dir!=NULL){
        sae->isleft = 1;
        sad->isleft = 0;
        Arv_left(sae,sae->esq,sae->dir);
        Arv_left(sad,sad->esq,sad->dir);
    }
}
//estrutursa de uma lista
typedef struct lista{
    int cd;
    char a;
    struct lista *prox;
}Lista;
 
//imprime lista
void imprime(Lista* lis){
    while(lis!=NULL){
        printf("%c(%d) ", lis->a, lis->cd);
        lis = lis->prox;
    }
}
//herda o codigo da subarvore 'pai' para a subarvore 'filha'
void guardacodigo(Arv* v,Arv* sa,int n){
    int i;
    if(sa!=NULL){ 
        for(i=0;i<n;i++)
            sa->codigo[i] = v->codigo[i];
        sa->codigo[n] = sa->isleft;
        guardacodigo(sa,sa->esq,n+1);
        guardacodigo(sa,sa->dir,n+1);
    }
}
 
void criatabd(Tabela *tabd, Arv *v, int n){
    int i=0;
    if(v!=NULL){
        if(v->esq==NULL){
            while(v->codigo[i]==0||v->codigo[i]==1){
                tabd[n].codigo[i]=v->codigo[i];
                i++;
            }
            tabd[n].a = v->c;
            n++;
            
        }
        criatabd(tabd,v->dir,n);
    }
}
 
void criatabe(Tabela *tabe, Arv *v, int n){
    int i=0;
    if(v!=NULL){
        if(v->esq==NULL){
            while(v->codigo[i]==0||v->codigo[i]==1){
                tabe[n].codigo[i]=v->codigo[i];
                i++;
            }
            tabe[n].a = v->c;
            n++;
            
        }
        //system("pause");
        criatabe(tabe,v->esq,n);
    }    
} 
int main(){
    char mensagem[50];
    int i;
    Arv *lis =cria_lst(), *a;
    Tabela tabd[50], tabe[50];
    printf("Digite a mensagem: ");
    gets(mensagem);
    //conta a qte de caracter e usa a funcao para contar a frequencia dos caracteres
    for(i=0;i<strlen(mensagem);i++)
        lis = contafreq(mensagem,mensagem[i],lis);
    lst_imprime(lis);
    
    int j;
    for(i=0;i<50;i++){
        for(j=0;j<10;j++){
            tabe[i].codigo[j] = -5;
            tabd[i].codigo[j] = -5;
        }
    }
    while(Nos(lis->prox)>1){
        
        a = cria_arv(retira_menor(lis),retira_menor(lis));
        lis = lst_insereA(a,lis);
    }
    
    a = lis->prox;
    
    printf("\n\n\n");
    Arv_left(a,a->esq,a->dir);
    arv_imprime(a);
    guardacodigo(a->esq,a->esq,0);
    guardacodigo(a->esq,a->dir,0);
    criatabe(tabe,a->esq,0);
    criatabe(tabd,a->dir,0);
    i=0;
    
    while(tabd[0].codigo[i]==0||tabd[0].codigo[i]==1){
        printf("%d",tabd[0].codigo[i]);
        i++;
    }
    printf("\nCaracter: %c", tabd[0].a);
    
    //system("pause");
    return 0;
}

Comments