经常用到链表,但每次写都不那么顺利,终于有点时间整理一下,把感觉写的不错的代码拿出来分享,希望大家能指出问题,那我算没白写。 该链表以存放整型数据为例。
头文件:
#ifndef __LINK_H__
#define __LINK_H__

#define ERROR ( -1 )
#define OK ( 0 )

#define TRUE ( 1 == 1 )
#define FALSE ( !TRUE )


typedef int BOOL;
typedef int elem_t; //定义元素的数据类型

typedef struct node

...{
elem_t data;
struct node * next;
}tagNode_t,tagList_t;



/**//* 把已经存在的头节点进行初始化为一个空链表 */
void initList ( tagList_t * list );

/**//* 销毁链表 */
void destroyList( tagList_t * list );


/**//* 将链表重置为空 */
void clearList( tagList_t * list );

BOOL listEmpty( tagList_t * list );

int listLength( tagList_t * list );


/**//* 得到指定位置 pos 的元素,如果顺利得到则返回TRUE,否则返回 FALSE*/
BOOL getElem( tagList_t * list, int iPos, elem_t * e);


/**//* 返回第一个满足 compare 关系的元素的位置,如果不存在则返回 -1 */
int locateElem( tagList_t * list, elem_t e,
BOOL (*compare)(elem_t e1,elem_t e2));


/**//* 将元素e插到链表的指定位置 ,若iPos > listLength() 则插到最后*/
BOOL listInsert( tagList_t * list, int iPos, elem_t e );

BOOL listInsertFront( tagList_t * list, elem_t e );


/**//* 按照费递减序插入元素 e */
BOOL listSortInsert( tagList_t * list, elem_t e );

BOOL listDeleteFront( tagList_t * list, elem_t * e );


/**//* 用visit 函数遍历链表 */
void listTraverse( tagList_t * list, void (*visit)(elem_t e));


#endif
源文件:

#include <stdio.h>
#include <stdlib.h>
#include <assert.h>
#include "link.h"



/**//* 把已经存在的头节点进行初始化为一个空链表 */
void initList ( tagList_t * list )

...{
list->next = NULL;
}

/**//* 销毁链表,没有释放头结点 */
void destroyList( tagList_t * list )

...{
tagNode_t * pn = NULL;
assert( list != NULL );
pn = list->next;
while( pn != NULL)

...{
list->next = pn->next;
free( pn );
pn = list->next;
}
}


/**//* 将链表重置为空 */
void clearList( tagList_t * list )

...{
destroyList( list ); //同 销毁
}

BOOL listEmpty( tagList_t * list )

...{
return ( NULL == list->next );
}

int listLength( tagList_t * list )

...{
int iLen = 0;
tagNode_t * ptn = NULL;
assert( list != NULL );
ptn = list->next;
while( ptn != NULL )

...{
iLen += 1;
ptn = ptn->next;
}
return iLen;
}


/**//* 得到指定位置 pos 的元素,如果顺利得到则返回TRUE,否则返回 FALSE*/
BOOL getElem( tagList_t * list, int iPos, elem_t * e)

...{
BOOL bRet = FALSE;
tagNode_t * ptn = NULL;
assert( list ); //list != NULL
if( list || ( iPos >= 0 ) )

...{
ptn = list->next;
while( iPos-- && ptn )

...{
ptn = ptn->next;
}
if( ptn != NULL )

...{
*e = ptn->data;
bRet = TRUE;
}
}
return bRet;
}


/**//* 返回第一个满足 compare 关系的元素的位置,如果不存在则返回 0 */
int locateElem( tagList_t * list, elem_t e,
BOOL (*compare)(elem_t e1,elem_t e2))

...{
int iPos = 0;
tagNode_t * ptn = NULL;
assert( list ); //list != NULL
ptn = list->next;
while( ptn )

...{
iPos += 1;
if( compare( e, ptn->data ) )

...{
break;
}
ptn = ptn->next;
}
if( NULL == ptn )

...{
iPos = 0;
}
return iPos;
}


/**//* 将元素e插到链表的指定位置 ,若iPos > listLength() 则插到最后*/
BOOL listInsert( tagList_t * list, int iPos, elem_t e )

...{
BOOL bRet = FALSE;
tagNode_t * ptn = NULL, * pstNew = NULL;
assert( list ); //list != NULL
if( list || (iPos >= 0) )

...{
ptn = list->next;
while( iPos-- && ptn->next )

...{
ptn = ptn->next;
}

pstNew = ( tagNode_t * )malloc( sizeof( tagNode_t ) );
if( pstNew != NULL )

...{
pstNew->data = e;
pstNew->next = ptn->next;
ptn->next = pstNew;
bRet = TRUE;
}
}
return bRet;
}

BOOL listInsertFront( tagList_t * list, elem_t e )

...{
BOOL bRet = FALSE;
tagNode_t * pstNew =
( tagNode_t * )malloc( sizeof( tagNode_t ) );
assert( list );
if( pstNew != NULL )

...{
pstNew->data = e;
pstNew->next = list->next;
list->next = pstNew;
bRet = TRUE;
}
return bRet;
}


/**//* 按照非递减序插入元素 e */
BOOL listSortInsert( tagList_t * list, elem_t e )

...{
BOOL bRet = FALSE;
tagNode_t * ptn = NULL, * pstNew = NULL;
assert( list );
ptn = list;
while( ptn->next )

...{
if( ptn->next->data > e )

...{
bRet = TRUE;
break;
}
ptn = ptn->next;
}
pstNew = ( tagNode_t * )malloc( sizeof( tagNode_t ) );
if( pstNew != NULL)

...{
pstNew->data = e;
pstNew->next = ptn->next;
ptn->next = pstNew;
bRet = TRUE;
}

return bRet;
}

BOOL listDeleteFront( tagList_t * list, elem_t * e )

...{
BOOL bRet = FALSE;
tagNode_t * ptn = NULL;
if( list != NULL )

...{
ptn = list->next;
*e = ptn->data;
list->next = ptn->next;
free( ptn );
bRet = TRUE;
}
return bRet;
}


/**//* 用visit 函数遍历链表 */
void listTraverse( tagList_t * list, void (*visit)(elem_t e))

...{
tagNode_t * ptn = NULL, * pstNew = NULL;
assert( list );
ptn = list->next;
while( ptn )

...{
visit( ptn->data );
ptn = ptn->next;
}
}


测试文件:
include <stdio.h>
#include "link.h"

void tst_link()

...{
elem_t e;
tagList_t list;
printf("********Test Stack******** ");
initList( &list );
printf("IsEmpty: %s ",(listEmpty( &list ) ? "true":"false"));
listSortInsert( &list, 4 );
listSortInsert( &list, 3 );
printf("5 in pos: %d ",locateElem( &list,5,elemEqual ));
listSortInsert( &list, 5 );
printf("5 in pos: %d ",locateElem( &list,5,elemEqual ));
listSortInsert( &list, 7 );
listSortInsert( &list, 2 );
printf("getElem (3) %s : %d ",(getElem( &list, 3, &e )?"right":"error"),e);
printf("getElem (6) %s : %d ",(getElem( &list, 6, &e )?"right":"error"),e);
listPrint( &list );
printf(" ");
printf("len: %d ",listLength( &list ));
listDeleteFront( &list, &e );
printf("After delete front len: %d ",listLength( &list ));
printf("IsEmpty: %s ",(listEmpty( &list ) ? "true":"false"));
printf("5 in pos: %d ",locateElem( &list,5,elemEqual ));
destroyList( &list );
printf("IsEmpty: %s ",(listEmpty( &list ) ? "true":"false"));
}
