CAlgShareList.h
#ifndef _C_ALG_SHARE_LIST_H_
#define _C_ALG_SHARE_LIST_H_
#include <string.h>
#include <stdlib.h>
#include "CAlgCommon.h"
#ifdef __cplusplus
extern "C" {
#endif
#define ALG_SHARE_LIST_INVALID_POS (-1)
typedef struct _CAlgShareNode{
void * curr_data; /* node data pointer */
int prev; /* previous link No. */
int next; /* next link No. */
int curr; /* current link No. */
}CAlgShareNode;
typedef struct {
int head; /* list head */
int tail; /* list tail */
int elem_count; /* list element counts */
unsigned int elem_size; /* list size of each element */
}CAlgShareList;
typedef CAlgShareNode* (*AlgShareList_RealNode_F)(int);
typedef struct {
/* position to real node pointer convert function */
AlgShareList_RealNode_F real_node_f;
/* compare function. NOTE: pass position (int) to (Node*) */
Alg_Cmp_F cmp_f;
}CAlgShareList_F;
/**
* l->head, l->next is int index, may means postion
*/
static inline void CAlgShareList_ReSet(CAlgShareList* l, unsigned int elem_size)
{
l->head = l->tail = ALG_SHARE_LIST_INVALID_POS;
l->elem_count = 0;
l->elem_size = elem_size;
}
/**
* insert n to list after prev
*@prev previous position, link n to real_node(n)->next,
* if real_node(n) return NULL , means add to head
*@n make sure real_node(n) return valid pointer !!!
*@real_node position to node position converter, convert prev and n to CAlgShareNode*
*/
//static inline void CAlgShareList_Insert(CAlgShareList* l, int prev, int n, AlgShareList_RealNode_F real_node)
//{
// CAlgShareNode*p_prev, *p_n;
// p_prev = real_node(prev);
// p_n = real_node(n);
// if(p_prev)
// {
// p_n->prev = prev;
// p_n->next = p_prev->next;
// p_prev->next = n;
// }
// else
// {
// p_n->prev = ALG_SHARE_LIST_INVALID_POS;
// p_n->next = l->head;
// l->head = n;
// }
//
// p_n->curr = n;
// p_prev = real_node(p_n->next);
// if(p_prev)
// p_prev->prev = n;
//
// if(prev == l->tail)
// l->tail = n;
//
// l->elem_count ++;
//}
/**
* add n to list head
*@f function pointer methods
*@l the share list which n should add to
*@n make sure real_node_f(n) return valid pointer !!!
*@ret return the tail position
*/
//static inline int CAlgShareList_AddHead(CAlgShareList* l, int n, AlgShareList_RealNode_F real_node_f)
//{
// CAlgShareList_Insert(l, ALG_SHARE_LIST_INVALID_POS, n, real_node_f);
// return l->head;
//}
/**
* add n to list tail
*@f real node function methods
*@l the share list which n should add to
*@n make sure real_node_f(n) return valid pointer
*@ret return the tail position
*/
//static inline int CAlgShareList_AddTail(CAlgShareList* l, int n, AlgShareList_RealNode_F real_node_f)
//{
// CAlgShareList_Insert(l, l->tail, n, real_node_f);
// return l->tail;
//}
/**
* find the node with data
*@f function pointer methods, use f.cmp_f() to compare
*@l the share list which n should add to
*@data make sure real_node_f(n) return valid pointer
*@ret return node position if found, else return ALG_SHARE_LIST_INVALID_POS
*/
static inline int CAlgShareList_Find(CAlgShareList_F f, CAlgShareList* l, void* data)
{
CAlgShareNode* tmp = f.real_node_f(l->head);
int rc = l->head;
while(tmp)
{
if(0 == f.cmp_f(tmp->curr_data, data, l->elem_size))
return rc;
rc = tmp->next;
tmp = f.real_node_f(tmp->next);
}
return ALG_SHARE_LIST_INVALID_POS;
}
/**
* remove node n from list
*@l the share list which n should add to
*@n make sure real_node_f(n) return valid pointer
*@f function pointer methods
*/
static inline int CAlgShareList_RemoveNode(CAlgShareList* l, int n, AlgShareList_RealNode_F real_node)
{
CAlgShareNode* curr = real_node(n);
CAlgShareNode* tmp;
if( curr == NULL) return -1;
if(n == l->head)
l->head = curr->next;
if(n == l->tail)
l->tail = curr->prev;
if(tmp= real_node(curr->prev))
tmp->next = curr->next;
if(tmp= real_node(curr->next))
tmp->prev = curr->prev;
l->elem_count --;
return 0;
}
///**
// * remove head node from list
// *@l the share list which n should add to
// *@f function pointer methods
// *@ret return the head node position
// */
//static inline int CAlgShareList_RemoveHead(CAlgShareList_F f, CAlgShareList* l)
//{
// int head = l->head;
// CAlgShareList_RemoveNode(l, l->head, f.real_node_f);
// return head;
//}</