Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- //grafo testar o caso SKKKK
- #include <stdio.h>
- #include <stdlib.h>
- #include <string.h>
- #define tamanho_heap 1000000
- typedef struct No{
- char tipo,memoria;
- int l,r;
- }no;
- char str[82000];
- no heap[tamanho_heap];
- int hp;
- int montaGrafo(int raiz,char* str, int b, int e){
- if(b == e){
- if(hp >= tamanho_heap){
- printf("Memoria insuficiente!");
- exit(1);
- }
- int pos=hp++;
- heap[pos].tipo=str[b];
- heap[pos].l=heap[pos].r=-1;
- return pos;
- }
- int i,ret;
- for( i=b; i<=e; i++){
- if(str[i]!='('){
- ret = montaGrafo(-1,str,i,i);
- }
- else{
- int j=i+1,total=1;
- while(total){
- if(str[j]=='(') total++;
- else if(str[j]==')') total--;
- j++;
- }
- ret = montaGrafo(-1,str,i+1,j-2);
- i=j-1;
- }
- if(raiz == -1) raiz=ret;
- else{
- if(hp >= tamanho_heap){
- printf("Memoria insuficiente!");
- exit(1);
- }
- int pos=hp++;
- heap[pos].tipo='@';
- heap[pos].l = raiz;
- heap[pos].r = ret;
- raiz = pos;
- }
- }
- return raiz;
- }
- int reduziu,atualizarRaiz;
- // 5 por que no pior caso eu vou precisar de um para saber o tipo S ou K / 3 para os operadores a b c no caso do S/ e outro para saber o retorno;
- void fazReducao(int raiz){
- int elements[6];
- int i,aux=raiz;
- int pos1, pos2, pos3,pos4;
- for(i=0; i<6; i++) elements[i]=-1;
- while(raiz!=-1){
- for(i=6; --i;){
- elements[i]=elements[i-1];
- }
- elements[0]=raiz;
- raiz = heap[raiz].l;
- }
- //printf("%c\n",heap[elements[0]].tipo);
- //for(i=0; i<5; i++) printf("%d ",elements[i]);
- //puts("");
- switch(heap[elements[0]].tipo){
- case 'K':
- if(elements[1]==-1 || elements[2]==-1) return;
- reduziu=1;
- if(elements[3]==-1){
- atualizarRaiz=heap[elements[1]].r;
- }
- else{
- heap[elements[3]].l=heap[elements[1]].r;
- }
- break;
- case 'S':
- if(elements[1]==-1 || elements[2]==-1 || elements[3]==-1) return;
- reduziu=1;
- // precisa checar essa condicao, nao tenho certeza se eh realmente 2 mais faz mais sentido >.<
- if(hp+2 >= tamanho_heap){ // +2 pq o ponteiro hp sempre ta uma posicao a frente entao eu ja tenho um @ mais vou precisar de + 2.
- printf("Memoria insuficiente!");
- exit(1);
- }
- pos1 = hp++;
- pos2 = hp++;
- pos3 = hp++;
- heap[pos1].tipo='@';
- heap[pos2].tipo='@';
- heap[pos3].tipo='@';
- heap[pos1].l = heap[elements[1]].r;
- heap[pos1].r = heap[elements[3]].r;
- heap[pos2].l = heap[elements[2]].r;
- heap[pos2].r = heap[elements[3]].r;
- heap[pos3].l = pos1;
- heap[pos3].r = pos2;
- //for(i=0; i<5; i++) printf("%d ",elements[i]);
- //puts("");
- if(elements[4]==-1){
- //puts("Entrou aqui");
- atualizarRaiz=pos3;
- }
- else{
- heap[elements[4]].l=pos3;
- }
- break;
- case 'I':
- if(elements[1]==-1) return;
- reduziu=1;
- if(elements[2]==-1){
- atualizarRaiz=heap[elements[1]].r;
- }
- else{
- heap[elements[2]].l=heap[elements[1]].r;
- }
- break;
- case 'B':
- //B a b c => a(bc)
- if(elements[1]==-1 || elements[2]==-1 || elements[3]==-1) return;
- reduziu=1;
- if(hp+3 >= tamanho_heap){ //
- printf("Memoria insuficiente!");
- exit(1);
- }
- pos1 = hp++;
- pos2 = hp++;
- heap[pos2].tipo='@';
- heap[pos2].l = heap[elements[2]].r; //left pra b
- heap[pos2].r = heap[elements[3]].r; // righ pra c
- heap[pos1].tipo='@';
- heap[pos1].l = heap[elements[1]].r;
- heap[pos1].r = pos2;
- if(elements[4]==-1){
- //puts("Entrou aqui");
- atualizarRaiz=pos1;
- }
- else{
- heap[elements[4]].l=pos1;
- }
- break;
- case 'C':
- //C a b c => acb
- if(elements[1]==-1 || elements[2]==-1 || elements[3]==-1) return;
- reduziu=1;
- pos1 = hp++;
- pos2 = hp++;
- heap[pos1].tipo='@';
- heap[pos1].l = heap[elements[1]].r; //left pra a
- heap[pos1].r = heap[elements[3]].r; // righ pra c
- heap[pos2].tipo='@';
- heap[pos2].l = pos1; //left pra pos1
- heap[pos2].r = heap[elements[2]].r; //righ pra b
- if(elements[4]==-1){
- //puts("Entrou aqui");
- atualizarRaiz=pos2;
- }
- else{
- heap[elements[4]].l = pos2;
- }
- break;
- case 's':
- //S' a b c d => a(bd)(cd)
- if(elements[1]==-1 || elements[2]==-1 || elements[3]==-1 || elements[4]==-1) return;
- reduziu=1;
- if(hp+4 >= tamanho_heap){
- printf("Memoria insuficiente!");
- exit(1);
- }
- pos1 = hp++;
- pos2 = hp++;
- pos3 = hp++;
- pos4 = hp++;
- heap[pos1].tipo='@';
- heap[pos2].tipo='@';
- heap[pos3].tipo='@';
- heap[pos4].tipo='@';
- heap[pos1].l = heap[elements[1]].r; // left para a - @1
- heap[pos2].l = heap[elements[2]].r; // left para b - @2
- heap[pos2].r = heap[elements[4]].r; // righ para d - @2
- heap[pos3].l = heap[elements[3]].r; // left para c - @3
- heap[pos3].r = heap[elements[4]].r; // righ para d de novo
- heap[pos1].r = pos2;
- heap[pos4].l = pos1;
- heap[pos4].r = pos3;
- if(elements[5]==-1){
- puts("Entrou aqui");
- atualizarRaiz=pos4;
- }
- else{
- puts("Entrou aqui2");
- heap[elements[5]].l=pos4;
- }
- break;
- case 'b':
- //B' a b c d => ab(cd)
- if(elements[1]==-1 || elements[2]==-1 || elements[3]==-1|| elements[4]==-1) return;
- reduziu=1;
- if(hp+3 >= tamanho_heap){
- printf("Memoria insuficiente!");
- exit(1);
- }
- pos1 = hp++;
- pos2 = hp++;
- pos3 = hp++;
- heap[pos1].tipo='@';
- heap[pos1].l = heap[elements[1]].r; // left pra a
- heap[pos1].r = heap[elements[2]].r; //righ pra b
- heap[pos2].tipo='@';
- heap[pos2].l = heap[elements[3]].r; // left para c - @1
- heap[pos2].r = heap[elements[4]].r; // righ para d - @1
- heap[pos3].tipo='@';
- heap[pos3].l = pos1;
- heap[pos3].r = pos2;
- if(elements[5]==-1){
- atualizarRaiz= pos3;
- }
- else{
- heap[elements[5]].l=pos3;
- }
- break;
- case 'c':
- //C' a b c d => a(bd)c
- if(elements[1]==-1 || elements[2]==-1 || elements[3]==-1|| elements[4]==-1) return;
- reduziu=1;
- if(hp+4 >= tamanho_heap){
- printf("Memoria insuficiente!");
- exit(1);
- }
- pos1 = hp++;
- pos2 = hp++;
- pos3 = hp++;
- heap[pos1].tipo='@';
- heap[pos1].l = heap[elements[1]].r; // left pra a
- heap[pos2].tipo='@';
- heap[pos2].l = heap[elements[2]].r; // left para b - @1
- heap[pos2].r = heap[elements[4]].r; // righ para d - @1
- heap[pos1].r = pos2;
- heap[pos3].tipo='@';
- heap[pos3].l = pos1; //left pra pos 1
- heap[pos3].r = heap[elements[3]].r; //righ pra c
- if(elements[5]==-1){
- atualizarRaiz= pos3;
- }
- else{
- heap[elements[5]].l=pos3;
- }
- break;
- }
- }
- void imprimePre(int raiz){
- if(raiz!=-1){
- imprimePre(heap[raiz].l);
- imprimePre(heap[raiz].r);
- printf("%c",heap[raiz].tipo);
- }
- }
- int main(){
- //freopen("in.txt","r",stdin);
- gets(str);
- int raiz= montaGrafo(-1,str,0,strlen(str)-1);
- reduziu=1;
- while(reduziu){
- reduziu=0;
- atualizarRaiz=-1;
- imprimePre(raiz);
- printf("\n");
- fazReducao(raiz);
- //printf("Raiz: %d\n",raiz);
- if(atualizarRaiz!=-1){
- raiz = atualizarRaiz;
- //puts("atualizou");
- }
- //printf("Raiz: %d\n",raiz);
- }
- printf("\n");
- imprimePre(raiz);
- puts("");
- return 0;
- }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement