All pastes #421619 Raw Edit

Stuff

public text v1 · immutable
·published 2007-04-02 22:38 UTC
rendered paste body
Trabalho de casa nº 4
Review of Attempt 1
Started on:	Sábado, 24 Março 2007, 00:04
Completed on:	Sábado, 31 Março 2007, 03:26
Tempo gasto:	7 dias 2 horas

1
Considere uma reimplementação do TAD fila usando os seguintes tipos para lista, fila:

struct lista{int val[34];}
struct fila {int cabeca, cauda; struct lista l;};

Comente (descreva o funcionamento) e indique quais as novas implicações desta abordagem, relativamente à que foi vista na aula prática.
Resposta:
Nesta abordagem é usado um array que vai conter os valores. Como uma fila é uma estrutura dinâmica e pode crescer infinitamente, esta abordagem torrna-se pouco eficiente uma vez que um array em C tem um tamanho fixo, Contudo, pode-se definir este array com um tamanho suficientemente grande para conter a fila.
Outro problema desta abordagem é o caso em que a fila pode estar cheia. Devemos então usar um array circular para evitar esse problema.

Podemos fazer operações como as seguintes para este tipo de dados.

struct fila f;
f.cabeca = 1;
f.cauda = 2;
f.l.val[0] = 1;
fl.val[1] = 2;

por exemplo o algoritmo de inserção poderia ser algo como:

void insere(fila * f, int x)
{
    if( f->cauda + 1 >= 34 )   
    {
        printf("\nEstá a inserir fora dos limites fila");
        exit(1);
    }
    f->l->val[f->cauda++ ] = x;
}  

2
Se a implementação do tipo lista fosse:

struct lista{ int val;
  lista *prox;
  lista *ant;};

1. Como chamaria a esse tipo de lista?
2. Quais as implicações na inserção e remoção?
3. Quais as vantagens de usar este tipo?
Resposta:
1. Lista Duplamente Ligada.

2. A inserção é feita em três etapas. Primeiro criamos o novo nó a inserir. Depois, procuramos a posição onde vamos inserir e, finalmente, fazemos os redireccionamentos dos apontadores de forma a que o nó fique 'ligado à lista'.
Usando um apontador auxiliar para determinar a posição onde se vai inserir o novo nó. A pesquisa termina com o apontador auxiliar a apontar para o nó que deve ser o proximo do nó que vamos inserir. Depois o próximo do novo nó passa a ser o nó onde estamos. O anterior do novo nó passa a ser o anterior do nó onde estamos. O seguinte do anterior do nó onde estamos passa a ser o novo nó e, finalmente, o anterior do nó onde estamos passa a ser o nó que estamos a inserir. (Isto se o nó for para inserir no meio da lista). Inserir na cabeça ou na cauda é semelhante ou até mais simples.
A remoção segue os mesmo tipo de redirecionamento de apontadores e pesquisa da inserção. Percorremos a lista até estarmos no nó anterior ao que vai ser removido.
Pomos esse nó a apontar para o próximo do próximo e o anterior deste ultimo a apontar para o nó onde estamos. Por fim libertamos da memoria o proximo do nó onde estamos (o nó a eliminar).

3. Uma das principais vantagens
relativamente às listas simples está na facilidade com
que é possível implementar as operações
de inserir, remover, etc., utilizando um só apontador
auxiliar, uma vez que a partir de um dado nó é sempre
possível aceder ao seu próximo e ao seu anterior.

Podemos deslocar-nos para o nó anterior ou para o nó
seguinte de um dado nó com igual facilidade. Além disso, uma lista duplamente ligada permite-nos remover um nó qualquer
da lista em tempo constante, usando apenas um ponteiro para esse nó.