/****************************************************/ /* Gestion de listes doublement chainees */ /* list.h */ /* */ /* Ecrit par : Daniel Lacroix (all rights reserved) */ /* */ /****************************************************/ #ifndef __LIST_H__ #define __LIST_H__ #include <general.h> /* pour les listes chainees */ typedef struct _List List; struct _List { pointer data; List *next; List *prev; }; /* Cree une nouvelle liste chainee. */ /* List *list_new() */ #define list_new() NULL /* Rajoute en tete de la liste pList l'element data. */ /* Renvoie le nouveau point d'entree de la liste. */ List *list_prepend(List *pList, pointer data); /* Rajoute en queue de la liste pList l'element data. */ /* Renvoie le nouveau point d'entree de la liste. */ List *list_append(List *pList, pointer data); /* Rajoute un element apres l'element before. Si l'element before */ /* n'est pas trouve alors le nouvel element sera rajoute a la fin. */ /* Renvoie ne nouveau point d'entree de la liste pList. */ List *list_insert_after_item(List *pList, pointer before, pointer data); /* Concatene la liste p2 a la liste p1 (p1 devant, p2 derriere) */ /* Renvoie la nouvelle liste cree. p1 et p2 sont consideres comme detruites */ List *list_concat(List *p1, List *p2); /* Empile data a la fin de la liste pList. */ /* Renvoie le nouveau point d'entree de la liste pList. */ /* void list_push(List *pList, pointer data); */ #define list_push(pList,data) list_append(pList,data) /* Depile le dernier element de la liste pList. */ /* Le dernier est place dans data et est sorti de la liste */ /* list_pop renvoie le nouveau point d'entree de la liste pList. */ List *list_pop(List *pList, pointer *data); /* Renvoie une copie de la liste pList. Les pointeurs data sont copies */ /* pas le contenu pointe. Il s'agit d'une liste avec des "alias" sur */ /* les elements de la premiere liste. */ List *list_copy(List *pList); /* Renvoie une copie de la liste pList. Les donnees contenu dans la liste sont copies */ /* avec la fonction copy_func. Elle recoit le pointeur de l'element d'origine et doit */ /* renvoyer un pointeur vers la copie. */ List *list_copy_full(List *pList, pointer (* copy_func)(pointer data)); /* Libere la liste (pas les elements) */ void list_free(List *pList); /* Libere la liste et appele la procedure free_func pour chaque elements */ void list_free_full(List *pList, void (* free_func)(pointer data)); /* Libere la liste et appele la procedure free (du C) pour chaque elements */ void list_free_full_simple(List *pList); /* Libere un element de la liste (pas ce que l'element pointe si c'est un pointeur) */ /* Renvoie le nouveau point d'entree de la liste. */ List *list_free_item(List *pList, pointer data); /* Libere un element de la liste (pas ce que l'element pointe si c'est un pointeur) */ /* Si l'element a ete libere alors done == TRUE sinon FALSE. */ /* Renvoie le nouveau point d'entree de la liste. */ List *list_free_item_with_check(List *pList, pointer data, boolean *done); /* Libere un element de la liste pList (pas la donnee pointe par data) */ /* Renvoie le nouveau point d'entree de la liste. */ List *list_free_chunk(List *pList, List *pToFree); /* Renvoi le nombre d'element contenue dans la liste */ /* Cette operation est realisee par comptage. */ uint32 list_nb_item(List *pList); /* Renvoie l'element a la position item_nb dans la liste pList */ /* Si l'element item_nb n'exite pas, la fonction renvoi NULL. */ /* item_nb commence a 1. */ pointer list_item(List *pList, uint32 item_nb); /* Renvoie la donnee correspondant a l'element de liste pList */ /* pointer list_data(List *pList); */ #define list_data(pList) ((pList)?(pList)->data:NULL) /* Renvoie l'element a la derniere position de la liste pList. */ /* Renvoie NULL si la liste est vide. */ /* List *list_last(List *pList); */ #define list_last(pList) ((pList)?(pList)->prev:NULL) /* Renvoie TRUE si la liste pList est vide. Renvoie FALSE sinon. */ /* boolean list_is_empty(List *pList); */ #define list_is_empty(pList) (pList == NULL) /* Renvoie TRUE si pCurrentList est au dela du dernier */ /* element de la liste pList. Sinon renvoie FALSE */ /* boolean list_is_end(List *pList, List *pCurrentList); */ #define list_is_end(pList,pCurrentList) (pCurrentList == NULL) /* Renvoie TRUE si pCurrentList est le premier */ /* element de la liste pList. Sinon renvoie FALSE */ /* boolean list_is_first(List *pList, List *pCurrentList);*/ #define list_is_first(pList,pCurrentList) ((pCurrentList) == pList) /* Renvoie TRUE si pCurrentList est le dernier */ /* element de la liste pList. Sinon renvoie FALSE */ /* boolean list_is_last(List *pList, List *pCurrentList); */ #define list_is_last(pList,pCurrentList)\ ((pCurrentList != NULL) && (pList != NULL) && ((pCurrentList)->next == pList)) /* Renvoie l'element apres pCurrentList dans la liste pList. */ /* Si on arrive au dela de la fin de la liste pList, renvoie NULL. */ /* List *list_next(List *pList, List *pCurrentList); */ #define list_next(pList,pCurrentList)\ (((pCurrentList)&&((pCurrentList)->next!=pList))?(pCurrentList)->next:NULL) /* Renvoie l'element avant pCurrentList dans la liste pList. */ /* Si l'element precedent est avant le premier element, renvoie NULL. */ /* List *list_prev(List *pList, List *pCurrentList); */ #define list_prev(pList,pCurrentList)\ (((pCurrentList)&&((pCurrentList)!=pList))?(pCurrentList)->prev:NULL) /* Deplace pCurrentList sur le prochain element de la liste pList */ /* Si on arrive a la fin pCurrentList devient NULL. */ /* void list_move_next(List *pList, List *pCurrentList); */ #define list_move_next(pList,pCurrentList) (pCurrentList = list_next(pList,pCurrentList)) /* Deplace pCurrentList sur l'element precedent de la liste pList */ /* Si on arrive avant le premier element alors pCurrentList devient NULL. */ /* void list_move_prev(List *pList, List *pCurrentList); */ #define list_move_prev(pList,pCurrentList) (pCurrentList = list_prev(pList,pCurrentList)) /* Trie la liste pList. La fonction cmp_func est utilise pour */ /* determine l'ordre. Elle doit renvoyer 0 si p1 pointe sur un */ /* element equivalent a p2. < 0 si p1 est inferieur a p2, >0 */ /* si p2 est superieur a p1. */ /* Renvoie la liste triee. */ List *list_sort(List *pList,int (* cmp_func)(pointer p1, pointer p2)); /* Insere l'element data dans la liste pList de maniere trie */ /* d'apres la fonction cmp_func. Elle doit renvoyer 0 si p1 */ /* pointe sur un element equivalent a p2. < 0 si p1 est */ /* inferieur a p2, >0 si p2 est superieur a p1. */ /* Renvoie le nouveau point d'entree de la liste. */ List *list_insert_sorted(List *pList,int (* cmp_func)(pointer p1, pointer p2), pointer data); /* Inverse l'ordre des elements de la liste pList */ /* Renvoie le nouveau point d'entree de la liste */ /* Cette operation peut ce faire pendant que l'on parcours */ /* (pas au sens multithreade du terme) */ /* la liste mais bien evidemment, le sens s'inverse. */ List *list_invert(List *pList); /* Recherche l'element de liste qui contient la premiere donnee data */ /* Renvoie l'element de liste si trouve, NULL sinon. */ List *list_find(List *pList, pointer data); /* Recherche l'element de liste qui contient la premiere donnee pour laquelle la */ /* fonction find_func renvoie TRUE. La fonction find_func prend en parametre le */ /* pointeur contenu dans la liste et le pointeur your_data qui est donne par */ /* l'utilisateur (pour y stocker ce dont il a besoin pour la comparaison). */ /* Renvoie l'element de liste si trouve, NULL sinon. */ List *list_find_full(List *pList, pointer your_data, boolean (* find_func)(pointer data, pointer your_data)); #endif /* __LIST_H__ */