新闻中心

EEPW首页 > 嵌入式系统 > 牛人业话 > C语言的那些小秘密之链表(二)

C语言的那些小秘密之链表(二)

作者:时间:2015-04-11来源:网络收藏

  除了个别天才程序员外,没有人一开始就能写出让人惊叹的代码,都是从模仿开始的!不要相信你身边的人说他能很轻松的自己编写出让人惊叹的代码而不用任何的参考资料,因为我相信在你我的身边没有这样的天才程序员,所以我们都选择从模仿和阅读源代码开始。就好比一个优秀的作家不是一开始就能写出好的文章,他也是阅读了很多优秀的文章之后才能写出优秀作品的。一开始我想详细的讲解双部分,但是我发现由于代码的原因,使得文章的篇幅过大,所以在此就选择一些易错和场用的知识点来进行讲解,如果一开始你发现阅读代码时很吃力,请不要放弃!我们要有毅力去把它消化掉,融会贯通之后再写出我们自己的双,当然我给出的仅仅只是一个参考而已。

本文引用地址:http://www.eepw.com.cn/article/272382.htm

  在此也要特地感谢下编程浪子朱云翔老师,阅读我博客后提出的宝贵意见,根据你的建议我接下来的博客中都把代码部分放到了代码框中,使得代码看起来更加的悦目。

  前一篇博客中我们讲解了单,那么接下来还是按照我们之前的安排讲解双链表部分, 在开始讲解之前,我们先来简单的回顾下上一篇博客中的双链表,双链表是链表的一种,它的每个数据结点中都有两个指针,分别指向直接后继和直接前驱。所以,从双向链表中的任意一个结点开始,都可以很方便地访问它的前驱结点和后继结点。对双链表做了一个简单的回顾之后那么接下来我们就来开始讲解双链表了,在这里我们也同样遵循一个原则,就是用简单易懂的代码和文字描述来讲解,我们要突出代码的重点是在编程的过程中我们的易错点。

  因为双链表的使用相对于单链表操作来说要复杂和常用些,所以在这里我采用逐渐添加功能模块的方法来进行讲解,从易到难,让读者理解起来更加轻松,同时我们在这里也使用我前面博客中提到的一些方法,学以致用嘛,学了就要在代码中尽可能的使用起来,要不然学了有什么用呢,接下来我们先来看看一个最为简单的双链表的创建。

  特此说明:

  1、如果在接下来的代码中发现一些不懂而我又没有给出提示信息的,如自己定义枚举型的数据结构DListReturn作为返回类型等,那么请你看我的前一篇博客《的那些小秘密之链表(一)》。

  2、由于文章在编辑的时候可以对代码部分使用颜色标记,但是发表后好像显示不出来,我试图修改,但还是不行,所以在此说明下,代码中被“” 和“ ”框起来的部分为有色部分。读者自己在阅读代码的时候注意下,自己对比也能找到新加入的代码。
#include <stdio.h>
#include <stdlib.h>

typedef enum _DListReturn
{
DLIST_RETURN_OK,
DLIST_RETURN_FAIL
}DListReturn;

typedef struct _DStu
{
int score;
}DStu;

typedef struct _DListNode
{
struct _DListNode* prev;
struct _DListNode* next;

DStu* data;
}DListNode;

typedef struct _DList
{
DListNode* head;
}DList;

typedef DListReturn (*DListPrintFunction)(void* data);

DListNode* dlist_node_create(void* data)
{
DListNode* node;
if((node = (DListNode*) malloc(sizeof(DListNode)))==NULL)
{
printf("分配空间失败!");
exit(0);
}

if(node != NULL)
{
node->prev = NULL;
node->next = NULL;
node->data =(DStu*)data;
}
return node;
}

DList* dlist_head_create(void)
{
DList* thiz;
if((thiz = (DList*)malloc(sizeof(DList)))==NULL)
{
printf("分配空间失败!");
exit(0);
}

if(thiz != NULL)
{
thiz->head = NULL;
}

return thiz;
}

DListReturn dlist_append(DList* thiz, void* data)
{
DListNode* node = NULL;
DListNode* cursor = NULL;

if((node = dlist_node_create(data)) == NULL)
{
return DLIST_RETURN_OK;
}

if(thiz->head == NULL)
{
thiz->head = node;

return DLIST_RETURN_OK;
}

cursor = thiz->head;
while(cursor != NULL && cursor->next != NULL)
{
cursor = cursor->next;
}

cursor->next = node;
node->prev = cursor;

return DLIST_RETURN_OK;
}

DListReturn dlist_print(DList* thiz, DListPrintFunction print)
{
DListNode* iter = thiz->head;

while(iter != NULL)
{
print(iter->data);
iter = iter->next;
}
printf("\n");
return DLIST_RETURN_OK;
}

DListReturn print_int(void* data)
{
DStu* ss=(DStu*)data;
printf("%d\t ", ss->score);

return DLIST_RETURN_OK;
}

int main(int argc, char* argv[])
{
int i = 0;

DList* dlist = dlist_head_create();

for(i = 0; i < 7; i++)
{
DStu* stu =(DStu*) malloc(sizeof(DStu));
stu->score = i;
dlist_append(dlist, (void*)stu);
}
dlist_print(dlist, print_int);

return 0;
}

  运行结果为:

  

 

  0 1 2 3 4 5 6

  Press any key to continue

  可能有的读者认为上面得代码有点复杂化了,其实不然,我们仅仅是写出了我们要讲解的双链表实现中最简单的部分,其实现的功能是创建一个链表,在链表末端添加结点,然后打印出链表中结点里存放的数据项,对代码的总体动能有了一个大概的了解之后,现在我们来逐一分析代码,为接下来添加功能模块打开思路。


上一页 1 2 3 下一页

关键词: C语言 链表

评论


相关推荐

技术专区

关闭