Chinaunix首页 | 论坛 | 博客
  • 博客访问: 299533
  • 博文数量: 76
  • 博客积分: 0
  • 博客等级: 民兵
  • 技术积分: 715
  • 用 户 组: 普通用户
  • 注册时间: 2015-05-20 20:38
文章分类
文章存档

2016年(20)

2015年(56)

分类: 嵌入式

2016-02-28 20:08:49


  1. 数据结构---线性表的链式表示和实现(一)
  2. 16年2月26日19:46:29
  3. 这一块的内容就是所谓的链表操作,对于这一块的内容需要熟练的掌握,以下的源程序是单链表的一些操作,对于双链表和循环链表,以及linux内核中的链表,我们将在后面写出来,现在先分析单链表:

  4. #include <stdio.h>
  5. #include <malloc.h>
  6. #include <stdlib.h>

  7. typedef struct Node {
  8.     int data;
  9.     struct Node *pNext;
  10. }NODE, *PNODE;

  11. /**
  12.  * Initialise the link_list.
  13.  * @param pHead [this link_list]
  14.  * @return [if success, return the address of the pHead]
  15.  */
  16. PNODE InitLink(PNODE pHead)
  17. {
  18.     pHead = (PNODE)malloc(sizeof(NODE));
  19.     if (!pHead)
  20.     {
  21.         printf("Cannot malloc memory for pHead.\n");
  22.         exit(-1);
  23.     }

  24.     pHead->pNext = NULL;

  25.     return pHead;
  26. }

  27. /**
  28.  * Judge the link_list is empty or not.
  29.  * @param pHead [this link_list]
  30.  * @return [if empty, return 1, if not empty, return 0]
  31.  */
  32. int IsLinkEmpty(PNODE pHead)
  33. {
  34.     return pHead->pNext ? 0 : 1;
  35. }

  36. /**
  37.  * Insert entry to the link_list.
  38.  * @param pHead [this link_list]
  39.  * @param pos [position]
  40.  * @param val [the entry value]
  41.  * @return [if success, return 1]
  42.  */
  43. int InsertLink(PNODE pHead, int pos, int val)
  44. {
  45.     int i = 0;
  46.     PNODE pTmp = pHead;
  47.     PNODE pNew;

  48.     if (pos < 1)
  49.     {
  50.         printf("Error position.\n");
  51.         exit(-1);
  52.     }

  53.     while (pTmp && i < pos - 1)
  54.     {
  55.         pTmp = pTmp->pNext;
  56.         i++;
  57.     }

  58.     pNew = (PNODE)malloc(sizeof(NODE));
  59.     if (!pNew)
  60.     {
  61.         printf("Cannot malloc memory for pNew.\n");
  62.         exit(-1);
  63.     }

  64.     pNew->data = val;
  65.     pNew->pNext = pTmp->pNext;

  66.     pTmp->pNext = pNew;

  67.     return 1;
  68. }

  69. /**
  70.  * Delete entry of the link_list.
  71.  * @param pHead [this link_list]
  72.  * @param pos [position]
  73.  * @param val [the value of the deleted entry]
  74.  * @return [if success, return 1]
  75.  */
  76. int DeleteLink(PNODE pHead, int pos, int *val)
  77. {
  78.     PNODE pTmp = pHead;
  79.     PNODE q;
  80.     int i = 0;

  81.     if (pos < 1)
  82.     {
  83.         printf("Error position.\n");
  84.         exit(-1);
  85.     }

  86.     while (pTmp && i < pos - 1)
  87.     {
  88.         pTmp = pTmp->pNext;
  89.         i++;
  90.     }

  91.     q = pTmp->pNext;
  92.     *val = q->data;
  93.     pTmp->pNext = q->pNext;
  94.     free(q);

  95.     return 1;
  96. }

  97. /**
  98.  * Traverse this link_list.
  99.  * @param pHead [this link_list]
  100.  */
  101. void TraverseLink(PNODE pHead)
  102. {
  103.     PNODE pTmp;

  104.     pTmp = pHead->pNext;
  105.     while (pTmp)
  106.     {
  107.         printf("%d ", pTmp->data);
  108.         pTmp = pTmp->pNext;
  109.     }
  110.     printf("\n");
  111. }

  112. int main(int argc, char const *argv[])
  113. {
  114.     PNODE pHead = NULL;
  115.     int val;

  116.     pHead = InitLink(pHead);
  117.     if (IsLinkEmpty(pHead))
  118.     {
  119.         printf("The link_list is empty.\n");
  120.     }
  121.     InsertLink(pHead, 1, 1);
  122.     InsertLink(pHead, 1, 2);
  123.     InsertLink(pHead, 1, 3);
  124.     InsertLink(pHead, 1, 4);
  125.     InsertLink(pHead, 1, 5);
  126.     InsertLink(pHead, 4, 33);
  127.     TraverseLink(pHead);
  128.     if (IsLinkEmpty(pHead))
  129.     {
  130.         printf("The link_list is empty.\n");
  131.     }
  132.     if (DeleteLink(pHead, 4, &val))
  133.     {
  134.         printf("The delete value is %d.\n", val);
  135.     }
  136.     TraverseLink(pHead);
  137.     if (DeleteLink(pHead, 3, &val))
  138.     {
  139.         printf("The delete value is %d.\n", val);
  140.     }
  141.     TraverseLink(pHead);
  142.     return 0;
  143. }

  144. 程序的运行结果如下所示:
  145. The link_list is empty.
  146. 5 4 3 33 2 1
  147. The delete value is 33.
  148. 5 4 3 2 1
  149. The delete value is 3.
  150. 5 4 2 1

  151. 对于这一块,有一个C语言的指针问题没有掌握,在上述程序中,刚开始是这样的:
  152. void InitLink(PNODE pHead)
  153. {
  154.     pHead = (PNODE)malloc(sizeof(NODE));
  155.     if (!pHead)
  156.     {
  157.         printf("Cannot malloc memory for pHead.\n");
  158.         exit(-1);
  159.     }

  160.     pHead->pNext = NULL;
  161. }
  162. 然后在main函数中是这样的:
  163. int main(int argc, char const *argv[])
  164. {
  165.     PNODE pHead = NULL;
  166.     int val;

  167.     InitLink(pHead);
  168.     InsertLink(pHead, 1, 1);
  169.     InsertLink(pHead, 1, 2);
  170.     。。。。。。
  171.     return 0;
  172. }

  173. 在调试的时候,它总提示在InsertLink(pHead, 1, 1); 这个函数中出错的。好好思考这个问题。在InitLink()这个函数中,pHead是临时变量,是储存在栈中的,当执行完这个函数以后,pHead的值会被释放,但是通过malloc动态分配的内存它不会释放,但是如果pHead释放的话,我们就找不到这个动态分配的内存地址,这时候,main函数中的pHead仍为空,没有赋值,所以在下面的插入操作中将要出错。


    但是如果我想把这个pHead的值直接存进main函数中声明的pHead变量中,这个怎么改呢?如果想直接修改main函数中的pHead变量,就需要把它的地址传过去,就是如下所示的:

    void InitLink(PNODE pHead)

    {

        pHead = (PNODE)malloc(sizeof(NODE));

        if (!pHead)

        {

        printf("Cannot malloc memory for pHead.\n");

        exit(-1);

        }


        pHead->pNext = NULL;

    }

    然后在main函数中是这样的:

    int main(int argc, char const *argv[])

    {

        PNODE pHead = NULL;

        int val;


        InitLink(&pHead);

        InsertLink(pHead, 1, 1);

        InsertLink(pHead, 1, 2);

        。。。。。。

        return 0;

    }

    这样在main函数中就不需要采用pHead = InitLink(pHead);的形式。


    总结一下:

    以这个InitLink()函数为例,比如在main函数中声明了一个PNODE pHead = NULL;变量,

    1)如果想要初始化这个变量,就需要对这个变量中的一些元素进行修改,所以需要传进去pHead变量的指针,在main函数中就需要这样的形式:InitLink(&pHead);

    2)如果不想给这个InitLink()函数传递指针,只是把这个PNODE 类型的pHead传进去,那么就需要在main函数中采取这样的形式:pHead = InitLink(pHead);

    同时,需要在这个InitLink()函数中返回这个pHead的地址。



阅读(1374) | 评论(0) | 转发(0) |
给主人留下些什么吧!~~