i'm making the ADT List Iterator
in C
.
When I use the primitive to print the list to the beginning they work correctly. But then, inside the main, I want to create the iterator over the list and look if the delete primitive works(i't works correctly) but then I want to print the list again with print_list_iterator()
again, it doesn't works.
I have my structs like this:
typedef struct node{
struct node *next;
void *data;
}nodo_t;
typedef struct list{
struct node *head;
}list_t;
typedef struct iterator{
node_t **pn;
}list_iterator_t;
These are the primitives of the ADT Iterator
that i am working with;
list_iterator_t * list_iterator_create(list_t * l){
struct iterator *li = malloc(sizeof(struct iterator));
if(li == NULL)
return NULL;
li->pn = &(l->head);
return li;
}
bool list_iterator_next(list_iterator_t *li){
if(*li->pn == NULL){
return false;
}
*li->pn = (*li->pn)->next;
return true;
}
void *list_iterator_current(const list_iterator_t *li){
if((*li->pn) == NULL){
return NULL;
}
return (*li->pn)->data;
}
Here my primitive to delete de iterator;
void *list_iterator_delete(lista_iterator_t *li){
if(*li->pn == NULL)
return NULL;
struct node *aux;
void *aux_data = (*li->pn)->data;
aux = (*li->pn);
*li->pn = (*li->pn)->next;
free(aux);
return aux_data;
}
Then, if i want to print the list i'm using:
void print_list_iterator(lista_t * l){
for(list_iterator_t *li =list_iterator_create(l);
!list_iterator_finish(li);
list_iterator_next(li)
){
int *e = list_iterator_current(li);
printf("%d -> ",*e);
}
}
If I use the print_list_iterator()
, then in the main it doesn't let me create an iterator on the same list, and use my primitives.
Any ideas?
By the way, I would like to know if these primitives are well implemented.
Function test in the main: int main(){
list_t *dest = list_create();
list_iterator_t *iter = list_iterator_create(dest);
int vector[] = {88,99,1,0,5,106,22,44,56,3,5,6,3,4,6};
size_t vector_size = sizeof(vector)/sizeof(vector[0]);
for(size_t i=0; i<vector_size; i++)
list_append(dest, vector +i);
list_iterator_delete(iter);
list_iterator_delete(iter);
list_iterator_delete(iter);
list_iterator_delete(iter);
print_list_iterator(dest);
In terminal:
MacBook-Air: UltraT$ gcc iterator_double_pointers.c -std=c99 -Wall -pedantic -o it2
MacBook-Air: UltraT$ ./it2
5 -> 106 -> 22 -> 44 -> 56 -> 3 -> 5 -> 6 -> 3 -> 4 -> 6 ->
So, my function are working right, but: If I call the print function (which is actually a function that runs through the list with the iterator primitives, that's why I shared the iterator primitives since there may be some error there)
print_list_iterator(destino);
list_iterator_delete(iter);
print_list_iterator(destino);
list_iterator_delete(iter);
list_iterator_delete(iter);
list_iterator_delete(iter);
The result in terminal:
MacBook-Air:tp2 UltraT$ ./it2
88 -> 99 -> 1 -> 0 -> 5 -> 106 -> 22 -> 44 -> 56 -> 3 -> 5 -> 6 -> 3 -> 4 -> 6 ->
It does not work.
That is why my function of eliminating sometimes works and sometimes not. I don't know where the problem is if in the print function (which actually goes through the list) or in the delete function
Finally, I solved it by using *prev and *curr(current node). In the future I want to change the function to use it with double pointers.
struct list_iterator{
node_t *prev;
node_t *curr;
list_t *l_iter;
};
typedef struct list_iterator list_iterator_t
void * delete_iterator_list(list_iterator_t * li) {
if (list_iterator_finish (li))
return NULL;
struct node * aux_node;
void * data;
if (! li-> prev) {
data = li-> curr-> data;
aux_node = li-> curr;
li-> l_iter-> head = aux_node-> next;
li-> curr = li-> l_iter-> head;
}
else if (li-> curr-> next == NULL) {
data = li-> curr-> data;
aux_node = li-> curr;
li-> curr = li-> curr-> next;
li-> prev-> next = li-> curr;
}
else {
data = li-> curr-> data;
aux_node = li-> curr;
li-> curr = li-> curr-> next;
li-> prev-> next = li-> curr;
}
free (aux_node);
return data;