You are on page 1of 19

Faculdade Santa Terezinha Anhanguera Estrutura de Dados Prof.

Joelson Jnior

Atividades Prticas Supervisionadas

Ariel Pereira Souza RA 2505004039 Alex Francisco Soares RA 2547453866 Rafael Bomfim RA 2504071494 Israel Dillas Soares RA 11553598887 Francisco Wanderson RA 1191425998

Taguatinga, 2012

Sumrio

Introduo______________________________________________ 2 Resoluo do caso_________________________________________ 2 Descrio das Funes______________________________________ 4 Funo Recursiva__________________________________________12 Referncias Bibliogrficas____________________________________ 17

Introduo

Neste trabalho sobre blocos, fica explicito os usos de recursos presentes das listas encadeadas. Uma lista encadeada uma representao de uma sequncia de objetos na memria do computador. Cada elemento da sequncia armazenado em uma clula da lista: o primeiro elemento na primeira clula, o segundo na segunda e assim por diante.

Resoluo do caso A proposta pede um programa para manipular os blocos, contendo uma lista de blocos A e com informaes e seguido por uma sequncia de comandos passados pelo usurio por um arquivo texto. Usando o comando FILE onde o programa pode ler e alterar informaes de arquivo texto tendo como meio de transporte um ponteiro que ter a funo de ler e incluir informaes do arquivo texto. O programa tem a funo de pegar o numero com a sequncia de comandos passada pelo usurio: Ex: - Mover : Este comando ser criado uma funo para colocar o bloco A no topo do monte onde est o bloco B retornando eventuais blocos que j estiverem sobre A s suas posies originais. - Acima: Este comando ser criado uma funo para colocar o bloco A juntamente com todos os blocos que estiverem sobre ele em cima do bloco B retornando eventuais blocos que j estiverem sobre B as suas posies originais. - Topo: Este comando ser criado uma funo para colocar o bloco A no topo do monte onde est o bloco B retornando eventuais blocos que j estiverem sobre A s suas posies originais.

- Empilhar: Este comando ser criado uma funo para colocar o bloco A juntamente com todos os blocos que estiverem sobre ele em cima do bloco B retornando eventuais blocos que j estiverem sobre B as suas posies originais.

- Encontrar maior: Este comando ser criado uma funo para procurar o maior dos elementos A e B e os ponteiros para as clulas que contm os mesmos.

- Sair: Este comando ser efetuado a finalizao da leitura do arquivo texto.

Aps pegar o comando do arquivo texto e passado por ponteiro por vrios critrios onde so separados os comandos dos nmeros. Haver funes para cada comando especifico aonde vai fica A quantidade de blocos dentro do arquivo texto tem o limite, a partir de zero e menor de 24. Onde vai estar definida a quantidade dentro do arquivo texto arquivo sada, escrito na primeira linha.

O programa somente ira parar de ler a sequncia de comandos e s ira parar quando encontrar a palavra sair ento ser feito um condio que verificar a hora de parar a verificao.

Descrio das principais funes Funo CriaLista A funo recebe um ponteiro para TBloco chamado bloco e um int t que o tamanho da lista. alocada memria atravs do malloc. Essa funo chama a funo CriaListaVazia e depois a funo LInsere para inserir na lista o valor cada

elemento com a posio em que ele est. //Criao da lista. void CriaLista(TBloco* bloco, int t) { int i ; bloco->tam = t ; // t corresponde ao tamanho da lista bloco->lista = (TLista*)malloc(sizeof(TLista)*t); //Aloca memria para a lista com o tamanho t for ( i =0; i<t; i++) { FLVazia(&(bloco->lista[i])); //Cria a lista vazia . LInsere(&(bloco->lista[i]), i); } } Funo FLVazia

A funo recebe um ponteiro para TLista.[1] e aloca na memria. O ponteiro para a ultima posio passa a apontar para o da primeira posio e o da primeira passa a apontar para NULL, para indicar que no h nenhum elemento na lista.

//Inicializa uma lista vazia void FLVazia(TLista* pLista )

{ pLista->pPrimeiro = (Apontador) malloc ( sizeof (TipoCelula)) ; // Alocao na memria pLista->pUltimo = pLista->pPrimeiro ; //Faz o ultimo apontar o primeiro pLista->pPrimeiro->pProx = NULL; //Faz o ponteiro para o proximo apontar para NULL }

Funo MoveAacimaB void MoveAacimaB(TBloco* bloco , int a , int b) { Apontador pA, pB, pAntA , pAntB; int listaA ; int listaB ; if(a != b) //Compara se os blocos so diferentes { //Procura os blocos pA = ProcuraBloco(bloco, &pAntA, &listaA, a); pB = ProcuraBloco(bloco ,&pAntB, &listaB, b); if(listaA != listaB) //Compara se os blocos j no esto na mesma lista { if(pA != NULL && pB != NULL && pB->pProx != pA) //Compara se h

algum bloco em cima da mesa { if(pA->pProx != NULL) //Compara se h algum bloco em cima do que vai ser movimentado { Original(bloco, pA->pProx); //Retorna o bloco a posio original pA->pProx = NULL; //Faz o ultimo apontar para NULL } if(pB->pProx != NULL) //Compara se h algum bloco em cima do que vai ser movimentado { Original(bloco, pB->pProx); //Retorna o bloco a posio original pB->pProx = NULL; //Faz o ultimo apontar para NULL } pB->pProx = pA; //Coloca o bloco A em cima do bloco B (pAntA)->pProx = NULL; //Faz a mesa na posio correpondente ao bloco A apontar para NULL bloco->lista[listaA].pUltimo = NULL; //Faz o ultimo da lista vazia apontar para NULL bloco->lista[listaB].pUltimo = pA; //Faz o ultimo da lista B receber o novo ultimo da lista }

} } } Funo MoveAtopoB A funo recebe um ponteiro para o tipo TBloco chamado bloco e dois inteiros (a e b). So criadas variveis do tipo Apontador chamadas pA, pB, pAntA, pAntB e do tipo inteiro listaA e listaB. Comparamos se os blocos que sero procurados no so os mesmos. chamada a funo ProcuraBloco que retorna para as variveis pA e pB os ponteiros referentes aos blocos que se quer movimentar. Comparamos se os blocos no esto na mesma lista, se estiver no so feita modifiao. Comparamos se h algum bloco em cima do que ser movimentado, caso exista retorna os blocos para as posies originais e o prximo aponta para NULL. Atravs do while percorremos os blocos da lista onde est o bloco B at chegar ao topo e colocamos o bloco A em cima. //Coloca o bloco a no topo retornando blocos que j estiverem sobre a s suas posies originais. void MoveAtopoB(TBloco* bloco, int a, int b) { Apontador pA, pB, pAntA , pAntB; int listaA; int listaB; if(a != b) //Compara se os blocos so diferentes { //Procura os blocos

pA = ProcuraBloco(bloco, &pAntA, &listaA, a); pB = ProcuraBloco(bloco, &pAntB, &listaB, b); if(listaA != listaB) //Compara se os blocos j no esto na mesma lista { if(pA != NULL && pB != NULL) //Compara se h algum bloco em cima da mesa { if(pA->pProx != NULL) //Compara se h algum bloco em cima do que vai ser movimentado { Original(bloco, pA->pProx); //Retorna o bloco a posio original pA->pProx = NULL; //Faz o ultimo apontar para NULL } while (pB->pProx != NULL) // Percorre at chegar no ultimo da lista { pB = pB->pProx; } pB->pProx = pA; //Coloca o bloco A em cima da lista de blocos em cima de B (pAntA)->pProx = NULL; //Faz a mesa na posio correpondente ao bloco A apontar para NULL

bloco->lista[listaB].pUltimo = pA; //Faz o ultimo da lista B receber o novo ultimo da lista } } } } Funo EmpilharAacimaB

A recebe um ponteiro para o tipo TBloco chamado bloco e dois inteiros (a e b). Comparamos se os blocos que sero procurados no so os mesmos. Depois chamada a funo ProcuraBloco para retornar para as variveis pA e pB os ponteiros referentes aos blocos que se vamos movimentar. Se os estiverem esto na mesma lista no feita nenhuma modificao. Verifica se h algum bloco em cima da mesa e se h algum bloco em cima do que ser movimentado, caso exista retorna os blocos para as posies originais e aponta para o prximo apontar para NULL. Coloca o bloco A e a lista de blocos que esto em cima de A em cima do bloco B. Faz o ultimo da lista B receber o novo ltimo da lista.

void EmpilharAacimaB(TBloco* bloco, int a, int b) { Apontador pA, pB, pAntA, pAntB; int listaA; int listaB;

if(a != b) //Compara se os blocos so diferentes { //Procura os blocos pA = ProcuraBloco(bloco, &pAntA, &listaA, a); pB = ProcuraBloco(bloco, &pAntB, &listaB, b); if(listaA != listaB) //Compara se os blocos j no esto na mesma lista { if(pA != NULL && pB != NULL) { if(pB->pProx != NULL) //Compara se h algum bloco em cima do que vai ser movimentado { Original(bloco, pB->pProx); //Retorna o bloco a posio original pB->pProx = NULL; //Faz o ultimo apontar para NULL } pB->pProx = pA; //Coloca a lista de blocos que esto em cima de A em cima do bloco B (pAntA)->pProx = NULL; } } } }

Funo EmpilharAtopoB

A recebe um ponteiro para o tipo TBloco chamado bloco e dois inteiros (a e b). Cria variveis do tipo Apontador chamadas pA, pB, pAntA, pAntB e variveis do tipo int listaA e listaB. Comparamos se os blocos que sero procurados no so os mesmos. Depois chamamos a funo ProcuraBloco que retorna para as variveis pA e pB os ponteiros referentes aos blocos que iremos movimentar. Verificamos se os blocos no esto na mesma lista, se estiverm no feita nenhuma modificao. Atravs de um while percorre os blocos da lista onde est o bloco B at chegar ao topo e colocamos A e a lista de blocos que esto em cima de A em cima da lista de blocos que esto em B. . void EmpilharAtopoB(TBloco* bloco, int a, int b) { Apontador pA, pB, pAntA, pAntB; int listaA; int listaB; if(a != b) //Compara se os blocos so diferentes { //Procura os blocos

pA = ProcuraBloco(bloco, &pAntA, &listaA, a); pB = ProcuraBloco(bloco, &pAntB, &listaB, b); if(listaA != listaB) //Compara se os blocos j no esto na mesma lista { if(pA != NULL && pB != NULL) //Compara se h algum bloco em cima da mesa { while(pB->pProx != NULL) // Percorre at chegar no ultimo da lista { pB = pB->pProx; } pB->pProx = pA; (pAntA)->pProx = NULL bloco->lista[listaA].pUltimo = pAntA; while(pA->pProx != NULL) //Percorre at chegar no ultimo da lista { pA = pA->pProx ; } bloco->lista[listaB].pUltimo = pA; //O ultimo da lista B receber o novo ultimo da lista } }

} } Funo recursiva A funo recebe um ponteiro para o tipo TBloco chamado pBloco e um Apontador p. Se p for diferente de NULL, existem blocos em cima do bloco que se deseja movimentar. Esta funo chamada at que no exista mais blocos em cima do bloco desejado. Quando no houver mais blocos o ponteiro para o prximo vai apontar para NULL. //Funo recursiva para retornar os blocos para posies originais void Original (TBloco* pBloco , Apontador p) { if (p != NULL) { pBloco->lista[p->item.Chave].pPrimeiro->pProx = p; Original(pBloco, p->pProx); p->pProx = NULL; pBloco->lista[p->item.Chave].pUltimo = p; p->pProx = NULL; } }

Funo SalvaArquivo

criado um ponteiro para FILE chamado fp, que o caminho para o arquivo. Criado um int i, que ser ndice e um Apontador aux que ser necessrio para percorrer as posies. Abre o arquivo para a escrita. Utiliza uma estrutura for para percorrer o vetor de listas. Dentro do for existe outro for que percorre cada posio e escreve o item.Chave de saida .

void SalvaArquivo(TBloco* bloco, char* file) { FILE* fp; //Cria o caminho do arquivo int i; Apontador aux; // if((fp = fopen(file ,"w")) == NULL) // abre um arquivo de texto { printf("\nErro na criacao do arquivo txt de saida!\n"); exit(1); } // fp = fopen(file, "w" ); //Realiza a abertura do arquivo para escrita for(i=0; i<bloco->tam; i++) { fprintf(fp, "%d : ", i);

for(aux=bloco->lista[i].pPrimeiro->pProx; aux != NULL; aux = aux->pProx) { fprintf(fp, "%d ", aux->item.Chave); } fprintf(fp,"\n"); } fprintf(fp,"\n"); }

Main

O argv um ponteiro para uma matriz de strings. Cada string desta matriz um dos parmetros da linha de comando. para saber quantos elementos temos em argv que temos argc. Inicializamos as variveis necessrias e um ponteiro para FILE chamado fp que o caminho para o arqivo. alocado espao correspondente aos caracteres mover, empilhar, acima e topo. Chamamos a funo fscanf para ler do arquivo e sabermos de qual ser o tamanho da lista de vetores. Chamamos a funo CriaLista passando o endereo da varivel bloco do tipo TBloco e o inteiro numbloc para criao da lista no formato padro com o tamanho especificado no arquivo. Utilizamos outro fscanf para leitura dos blocos e dos movimentos que sero feitos com eles. Utilizamos uma estrutura de repetio while para realizar os movimentos que so passadas pelo arquivo. Aps isso o arquivo fechado com fclose e salvo utilizando a funo SalvaArquivo.

int main(int argc , char* argv[]) { TBloco bloco; char *x , *y; int numbloc, bloc1, bloc2; int listaA; int listaB; FILE * fp; fp = fopen ( argv[1], " r " ); /* Abre o arquivo de leitura por linha de comando */ x = ( char *) malloc ( sizeof ( char ) *5); y = ( char *) malloc ( sizeof ( char ) *5); fscanf(fp, "%d\n" ,&numbloc ); /*L um dado no arquivo que representa o tamanho */ CriaLista(&bloco , numbloc ); fscanf( fp , "%s %d %s %d\n" ,x,&bloc1 , y,&bloc2 ); /*Faz a leitura dos outros dados do arquivo */ while( ( strcmp (x , "sair"))!=0) /*Caso seja sair, fecha o arquivo, se no entra no while */ { /*Comparaes feitas para saber qual movimento ser realizado */ if( ( strcmp (x , "mover" ) )==0) {

if( ( strcmp (y , "acima" ) )==0) { MoveAacimaB(&bloco , bloc1 , bloc2 ); } else { MoveAtopoB(&bloco , bloc1 , bloc2 ); } } else { if( ( strcmp (y , "acima" ) )==0) { EmpilharAacimaB(&bloco , bloc1 , bloc2 ); } else { EmpilharAtopoB(&bloco , bloc1 , bloc2 ); } } fscanf( fp , "%s %d %s %d\n" ,x,&bloc1 , y,&bloc2 );

} fclose ( fp ); /*fecha o arquivo*/ SalvaArquivo(&bloco , argv [ 2 ] ); return 0; } Para executar o programas utilizamos linha de comando passando o nome do programa compilado (.exe) e os nomes dos arquivos de entrada e saida.

Referncia Bibliogrfica

Link: http://pt.wikipedia.org/wiki/Estrutura_de_dados

Link: http://pt.wikipedia.org/wiki/UML

Link: http://www.ime.usp.br/~pf/algoritmos/aulas/lista.html

PLT: Estruturas de Dados Usando C (Tenenbaum, Aaron M. MAKRON BOOKS).