双向环形链表
#ifndef DULIST_H
#define DULIST_H
/* 線性表的雙向鏈表存儲結構 */
typedef void * elemtype;
typedef struct dulnode
{ elemtype data;struct dulnode *prior,*next;
}dulnode,*dulinklist;
/*帶頭結點的雙向循環鏈表的基本操作(14個) */
void list_init(dulinklist *l);
void list_destory(dulinklist *l);
void list_clear(dulinklist l);
int list_empty(dulinklist l);
int list_length(dulinklist l);
int list_getelem(dulinklist l,int i,elemtype *e);
int list_locateelem(dulinklist l,elemtype e,int(*compare)(elemtype,elemtype));
int list_priorelem(dulinklist l,elemtype cur_e,elemtype *pre_e);
int list_nextelem(dulinklist l,elemtype cur_e,elemtype *next_e);
dulinklist list_get_elemp(dulinklist l,int i); /* 另加 */
int list_insert(dulinklist l,int i,elemtype e);
int list_delete(dulinklist l,int i,elemtype * e);
void list_traverse(dulinklist l,void(*visit)(elemtype));
void list_traverse_back(dulinklist l,void(*visit)(elemtype));#endif #include "includes.h"
#define OVERFLOW -1
#define ERROR -2
#define OK 1
#define true 1
#define false 0void list_init(dulinklist *l)
{ /* 產生空的雙向循環鏈表l */*l=(dulinklist)malloc(sizeof(dulnode));if(*l)(*l)->next=(*l)->prior=*l;elseexit(OVERFLOW);
}
void list_destory(dulinklist *l)
{/* 操作結果:銷毀雙向循環鏈表l */dulinklist q,p=(*l)->next; /* p指向第一個結點 */while(p!=*l) /* p沒到表頭 */{q=p->next;free(p);p=q;}free(*l);*l=NULL;
}
void list_clear(dulinklist l) /* 不改變l */
{ /* 初始條件:l已存在。操作結果:將l重置為空表 */dulinklist q,p=l->next; /* p指向第一個結點 */while(p!=l) /* p沒到表頭 */{q=p->next;free(p);p=q;}l->next=l->prior=l; /* 頭結點的兩個指針域均指向自身 */
}
int list_empty(dulinklist l)
{ /* 初始條件:線性表l已存在。操作結果:若l為空表,則返回true,否則返回false */if(l->next==l&&l->prior==l)return true;elsereturn false;
}
int list_length(dulinklist l)
{ /* 初始條件:l已存在。操作結果:返回l中數據元素個數 */int i=0;dulinklist p=l->next; /* p指向第一個結點 */while(p!=l) /* p沒到表頭 */{i++;p=p->next;}return i;
}
int list_getelem(dulinklist l,int i,elemtype *e)
{ /* 當第i個元素存在時,其值賦給e并返回OK,否則返回ERROR */int j=1; /* j為計數器 */dulinklist p=l->next; /* p指向第一個結點 */while(p!=l&&(p=p->next)){j++;}if(p==l||j>i) /* 第i個元素不存在 */return ERROR;*e=p->data; /* 取第i個元素 */return OK;
}int list_locate_elem(dulinklist l,elemtype e,int(*compare)(elemtype,elemtype))
{ /* 初始條件:l已存在,compare()是數據元素判定函數 *//* 操作結果:返回l中第1個與e滿足關系compare()的數據元素的位序。 *//* 若這樣的數據元素不存在,則返回值為0 */int i=0;dulinklist p=l->next; /* p指向第1個元素 */while(p!=l){i++;if(compare(p->data,e)) /* 找到這樣的數據元素 */return i;p=p->next;}return 0;
}int list_priorelem(dulinklist l,elemtype cur_e,elemtype *pre_e)
{ /* 操作結果:若cur_e是l的數據元素,且不是第一個,則用pre_e返回它的前驅, *//* 否則操作失敗,pre_e無定義 */dulinklist p=l->next->next; /* p指向第2個元素 */while(p!=l) /* p沒到表頭 */{if(p->data==cur_e){*pre_e=p->prior->data;return true;}p=p->next;}return false;
}int list_next_elem(dulinklist l,elemtype cur_e,elemtype *next_e)
{ /* 操作結果:若cur_e是l的數據元素,且不是最后一個,則用next_e返回它的后繼, *//* 否則操作失敗,next_e無定義 */dulinklist p=l->next->next; /* p指向第2個元素 */while(p!=l) /* p沒到表頭 */ {if(p->prior->data==cur_e){*next_e=p->data;return true;}p=p->next;}return false;
}dulinklist list_get_elemp(dulinklist l,int i) /* 另加 */
{ /* 在雙向鏈表l中返回第i個元素的地址。i為0,返回頭結點的地址。若第i個元素不存在,*//* 返回NULL */int j;dulinklist p=l; /* p指向頭結點 */if(i<0||i>list_length(l)) /* i值不合法 */return NULL;for(j=1;j<=i;j++)p=p->next;return p;
}
int list_insert(dulinklist l,int i,elemtype e)
{ /* 在帶頭結點的雙鏈循環線性表l中第i個位置之前插入元素e,i的合法值為1≤i≤表長+1 *//* 改進算法2.18,否則無法在第表長+1個結點之前插入元素 */dulinklist p,s;if(i<1||i>list_length(l)+1) /* i值不合法 */return ERROR;p=list_get_elemp(l,i-1); /* 在l中確定第i個元素前驅的位置指針p */if(!p) /* p=NULL,即第i個元素的前驅不存在(設頭結點為第1個元素的前驅) */return ERROR;s=(dulinklist)malloc(sizeof(dulnode));if(!s)return OVERFLOW;s->data=e;s->prior=p; /* 在第i-1個元素之后插入 */s->next=p->next;p->next->prior=s;p->next=s;return OK;
}int list_delete(dulinklist l,int i,elemtype *e)
{ /* 刪除帶頭結點的雙鏈循環線性表l的第i個元素,i的合法值為1≤i≤表長 */dulinklist p;if(i<1) /* i值不合法 */return ERROR;p=list_get_elemp(l,i); /* 在l中確定第i個元素的位置指針p */if(!p) /* p=NULL,即第i個元素不存在 */return ERROR;*e=p->data;p->prior->next=p->next;//???沒有考慮鏈表頭?鏈表尾?p->next->prior=p->prior;free(p);return OK;
}
void list_traverse(dulinklist l,void(*visit)(elemtype))
{ /* 由雙鏈循環線性表l的頭結點出發,正序對每個數據元素調用函數visit() */dulinklist p=l->next; /* p指向頭結點 */while(p!=l){visit(p->data);p=p->next;}printf("\n");
}void list_traverse_back(dulinklist l,void(*visit)(elemtype))
{ /* 由雙鏈循環線性表l的頭結點出發,逆序對每個數據元素調用函數visit()。另加 */dulinklist p=l->prior; /* p指向尾結點 */while(p!=l){visit(p->data);p=p->prior;}printf("\n");
}
?
轉載于:https://www.cnblogs.com/likeyiyy/p/3652030.html
總結
- 上一篇: Android 自定义Applicati
- 下一篇: (二)单元测试利器 JUnit 4