C语言——链表相关总结

一、链表创建

链表头插:

Node * creat_h ()
   {
     Node * pHead,* pNew;
     pHead=(Node*)malloc(sizeof(Node));
     pHead->next=NULL;
     printf("请输入正整数:");
     pNew=(Node*)malloc(sizeof(Node));
     scanf("%d",&pNew->date);
     while(pNew->date>0)
       {
         pNew->next=pHead->next;  //**
         pHead->next=pNew;//**

         pNew=(Node*)malloc(sizeof(Node));
         scanf("%d",&pNew->date);

       }
       free(pNew);
       return pHead;
   }

图解
这里写图片描述
标星号的为头插创建链表的核心。要强调一下:两句代码的顺序不能颠倒。结合图示,不难发现,若要是顺序颠倒,那么pHead的数据域被覆盖,以致于pNew指针域无法正常连接。

链表尾插:

Node * creat_wl()
  {
    Node * pHead,* pNew,*pEnd;
    pHead=pEnd=(Node * )malloc(sizeof(Node));
    pHead->next=NULL;
    pNew=(Node * )malloc(sizeof(Node));
    printf("请输入正整数:");
    scanf("%d",&pNew->date);
    while(pNew->date>0)
      {
        pEnd->next=pNew;
        pNew->next=NULL;
        pEnd=pNew;

        pNew=(Node *)malloc(sizeof(Node));
        scanf("%d",&pNew->date);
       } 
       free(pNew);
       return pHead;
  }
  • 对比观察代码不难发现:链表尾插比链表头插多了一个pEnd节点。
  • 链表尾插就是pEnd标记pNew前一个节点,在没有数据时,pEnd初始化为pHead(即第一次插入pNew的前一个节点),进行第一次连接,之后不断让pEnd后移,连接,实现链表尾插。

二、链表逆置

Node *Inversion(Node*phead)
{
    node *p,*q;
    q=phead->next;
    p=q->next;
    while(p)
    {
        q->next=p->next;//相当于删除操作
        p->next=phead->next; //头插
        phead->next=p;//头插

        p=q->next;//更新p的位置

    }
    return phead;

}
  • 链表逆置其实质就是链表的头插。可以理解为先进行一次删除操作,再将删除了的节点头插连接。
  • 纸上谈来终觉浅,绝知此事要躬行。所以自己一定要去画图,画图才能更好地理解链表的知识。

三、链表的增删改查

如果前面的知识掌握了,增删改查学起来是十分简单的。
增加:
void Add(Node * pHead)    //插入到指定元素后面 
  {
    Node * ptemp=pHead,*pNew;
    int n;
    printf("请输入你想插入在数字几后面:");
    scanf("%d",&n);
    while(ptemp&&ptemp->date!=n)//遍历链表查找指定数字
      ptemp=ptemp->next;
    if(ptemp==NULL)
      printf("%d未找到\n",n);
    else
      {
        pNew=(Node*)malloc(sizeof(Node));
        printf("请输入要插入的数字:"); 
        scanf("%d",&pNew->next);
        pNew->next=ptemp->next;   //**
        ptemp->next=pNew;    //**
      }
  }
  • 星号两句位置不可颠倒,否则就会因发生覆盖而无法正常插入。
删除:

核心代码:

ptemp1->next=ptemp->next;
  • 删除时先遍历链表,找到指定信息,执行核心代码,之后free掉删除的节点,删除即完成。
修改:

遍历到指定信息时,修改数据域。

查询:

实质就是遍历链表。

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
三种不同的方法,挺不错的! #include<stdio.h> #include<stdlib.h> #include<string.h> #define N 100 typedef struct SList { char data[N]; //字符数组 struct SList *next; //定义链表头指针 }SList,*ListPointer; /*typedef struct List { SList *head; }List,* ListPointer; */ void initList(ListPointer &lp) { lp=(SList *)malloc(sizeof(SList));//初始化链表 lp->next=lp; //链表的头指针指向本身,实现链表循环 } void output(ListPointer lp) // 自定义输出函数 { SList *ep; ep=lp; while(ep->next!=lp) //判定条件 当指针重新指向头指针输出结束 { ep=ep->next; printf("%s ",ep->data); } } void revert(ListPointer lp) // 链表的逆置 { SList *p,*q; p=lp;q=NULL;lp=NULL; while(p) { q=p->next; p->next=lp; lp=p; p=q; } /*方法二 SList *p,*q,*end; p=lp->next; q=p->next; end=p; while(q!=lp) { lp->next=q; q=q->next; lp->next->next=p; p=lp->next; } end->next=lp; */ } void add_char(char *p,ListPointer lp) //将输入的字符传递给链表 { SList * ep; ep=lp; while(ep->next!=lp) //判定条件 当指针重新指向头指针输出结束 { ep=ep->next; } ep->next=(SList *)malloc(sizeof(SList)); //开辟空间存储 strcpy(ep->next->data,p); //字符的传递 ep->next->next=lp; } void main() { ListPointer L; char str[N]; initList(L); printf("输入#以结束\n");//确定输入终止条件 while(1) { scanf("%s",str); if(*str=='#') //判定条件 { break; } add_char(str,L); } printf("初始序列为:"); output(L); printf("\n"); revert(L); printf("逆置后为:"); output(L); printf("\n"); }
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值