Vamos utilizar também uma lista de inteiros. Pegue agora os arquivos:
Examine os arquivos. Observe que ListaInteiros é um tipo abstrato, cuja representação
só é vista dentro de listainteiros.c
.
O programa usuário de uma lista só pode acessá-la através das operações oferecidas
em sua interface.
Considere o seguinte problema.
Imagine que você quer
calcular a soma e o produto dos elementos numa lista
já existente.
Você poderia fazer isso em testaLista.c
...?
Isso não é possível devido à estrutura de encapsulamento da lista. Vamos então estender o tipo abstrato ListaInteiros, incluindo um iterador baseado em corotinas, com o qual será possível realizar tarefas como a descrita.
Veja que há três funções na interface listainteiros.h
:
listainteiros.c
.
A função criaIterador
deve retornar uma nova corotina
cujo código (corpo) é uma função - iteraLista
-
que percorre a lista dada, fornecendo com yield
cada um dos seus elementos.
Um "esqueleto" dessa função já está no arquivo listainteiros.c
.
Note que ela é declarada como static
no arquivo
listainteiros.c
pois não deve ser usada diretamente
de fora desse arquivo.
Note que a lista só está sendo passada como argumento para a
função criaIterador
.
Para amarrar a lista passada à corotina criada, essa função
já deve fazer um primeiro resume
para poder passar
a lista como parâmetro para a função iteraLista
.
iteraLista
começa logo dando um yield
para
retornar o controle a criaIterador
.
Ao alcançar o final da lista, a função iteraLista
retorna
MININT (é um aviso para o usuário do iterador que a lista acabou...)
O retorno de criaIterador
é um ponteiro para a nova
corotina (do tipo CoroP
), mas como não queremos que
o programa usuário saiba disso, esse ponteiro é retornado como um void *
.
A função ativaIterador
recebe uma corotina, ativa
sua execução, e retorna o valor fornecido por ela.
Finalmente, destroiIterador
destrói a corotina
passada como argumento.
Escreva essas funções e teste-as em testaLista
,
escrevendo código para somar (e multiplicar) os elementos das
duas listas criadas pela main
.
Não esqueça de destruir os iteradores após usá-los
(eles não podem ser reusados, pois a função que é seu "corpo" terá
retornado!).
Uma sugestão é somar os elementos da primeira lista e multiplicar os
elementos da segunda...
Para compilar seu programa, você vai usar:
gcc -m32 -Wa,--execstack -o meuprog core.s corotinas.c listainteiros.c testaLista.c