数据结构单链表学习笔记

数据结构上机 单链表

  1. 尾插法创建链表
  2. 头插法创建链表
  3. 销毁链表
  4. 求链表长度
  5. 求单链表中第i个元素
  6. 在第i个节点前插入值为x的节点
  7. 在链表中查找元素值为x的节点
  8. 删除元素第i个元素节点
  9. 在递增有序的单链表l中插入一个值为x的元素保持递增有序
  10. 将单链表中的奇数项和偶数项分解开
  11. 求递增有序单链表中l1和l2的公共元素 放入新的单链表l3
  12. 删除重复元素
  13. 递增有序单链表L1、L2,不申请新结点,利用原表结点对2表进行合并,并使得合并后成为一个集合,合并后用L1的头结点作为头结点,删除L2的头结点,要求时间性能最好。

头文件

#include
#include
typedef struct link
{
	int  data;
	struct link *next;
}linklist;
//链表输出函数
void output(linklist *L)
{
    linklist *p;
    p=L;
    printf("该链表输出为");
    while(p!=NULL)
    {
        printf("%d\n",p->data);
        p=p->next;
    }
}
void output2(linklist *L)
{
    linklist *p;
    p=L->next;
    printf("该链表输出为");
    while(p!=NULL)
    {
        printf("%d\n",p->data);
        p=p->next;
    }
}

//头插法创建链表
linklist *CreateList_Front()
{
	linklist *head, *p;
	int x;
    head = NULL;
	printf("依次输入数据(‘-999’表示输入结束):\n");
	scanf("%d",&x);
	while(x!=-999)
	{
        p=(linklist*)malloc(sizeof(linklist));//不断的申请新的结点
		p->data = x;
		p->next = head;
		head = p;
		scanf("%d",&x);//头插法算法简单 核心就两句p->next = head;head = p;
	}
	output(head);
    return head;
}

//尾插法创建链表
linklist *CreateList_End()
{
	linklist *head, *p, *e;
	int x;
    head = NULL;
	e = NULL;
	printf("请依次输入数据('-999'表示输入结束):\n");
	scanf("%d",&x);
	while(x!=-999)
	{
		p = (linklist*)malloc(sizeof(linklist));
		p->data = x;
		if(head == NULL)		//先判断输入的是不是第一个节点
		{
			head = p;			
		}
		else
		{
			e->next = p;		//e始终指向输入的最后一个节点
		}
		e = p;
		scanf("%d",&x);		
	}
	if(e != NULL)				//如果链表不为空,则最后节点的下一个节点为空
	{
		e->next = NULL;
	}
	output(head);			//尾插法比头插法复杂一些,程序中要做两次判断,分别是判断第一个节点和最后一个节点的判断。且消耗多一个指针变量e。
    return head;
}
//摧毁链表
linklist *ReleaseLiList(linklist*sp)
{

	linklist  *spCurr,*spPrv;
	spPrv = sp;
	while (spPrv != NULL)
	{
		spCurr = spPrv -> next;
		free(spPrv);
		spPrv = spCurr;
	}
	return NULL;
}

//求链表长度
int Length (linklist*L)
{
    linklist *m=L;
    int len=0;
    if(m==NULL)
		return 0;
    while(m!=0)//指向下一个节点
    {
       len++;
       m=m->next;
    }
    printf("链表长度为%d",len);
}
//取单链表中的第i个元素
int finddata(linklist*L,int i)
{
   int x;
   int j=1;
   linklist *p;
   p=L;
   while(j!=i)
   {
    p=p->next;
    j++; //统计次数标志
   }
   x=p->data;
    printf("该元素输出为:%d\n",x);
}
//在第i个节点前插入值为x的节点 存疑 
int  interdata(linklist *L,int i,int x)
{
   int j=1;
   linklist *p,*s;//定义s方便进行插入操作
   p=L;//指针指向指针指的地方
   while(p->next!=0&&j!=i-1)
   {
       p=p->next;
       j++;
   }
   if (p->next == NULL || j > i)// 经过循环,若最终p为空,或i为0或负数时,都说明位置不合理;
    { 
        printf("Position Error\n");
        return 0;
    }
   s=(linklist*)malloc(sizeof(linklist));
   s->data=x;
   s->next=p->next;
   p->next=s;
   output(L);
}


//查找值为x的元素结点
linklist *listfind(linklist *L,int x)
{
  linklist *p=L;//指向头节点
  while(p->next)
  {
      if(p->next->data==x)//找到目标结点 进行删除操作
       {
          return p; //返回结点指针
       }
       else
       p=p->next;//继续遍历
  }
  return NULL;
  
}
//删除单链表中的第i个元素结点
linklist * deletedata(linklist *L, int i)
{
    linklist *u;
    linklist *p = L;
    int k=1;
    while (p->next!=0&&k!=i-1)
     {
        p = p->next;
        k++;  
     }
 
    if (p->next == NULL || p==NULL)// 经过循环,若最终p为空,或i为0或负数时,都说明位置不合理;
     { 
        printf("Position Error\n");
        return 0;
    }
    u=p->next;
    p->next=u->next;
    free(u);
    output(L);//输出函数
    return L;
}
//在递增有序链表中插入值为x的元素
void inclinklist(linklist *L,int x)
{
    linklist *u;
    linklist *p=L;
    while(p->next!=NULL&&p->next->data<x)
    {
        p=p->next;//不断搜索
    }
    u=(linklist*)malloc(sizeof(linklist));
    u->data=x;
    u->next=p->next;
    p->next=u;
    output(L);
}

//10.将单链表中的奇数和偶数分开 新表和旧表元素同时输出到屏幕上
void splitlinklist (linklist *l1)
{
    linklist *l2;
    linklist *l3;
	l2 = (linklist*) malloc (sizeof(linklist));
	l3 = (linklist*) malloc (sizeof(linklist));
	linklist *p,*q,*s;
	//p = l1;
    p = l1;
	q = l2;
	s = l3;
	q -> next = s ->next= NULL;

	while(p)
	{
		if(p->data % 2 == 1)//奇数
		{
			q->next = p;
			p = p->next;
			q = q->next;
		}
		else if(p->data%2 == 0)//偶数
		{
			s->next = p;
			s = s->next;
			p = p->next;
		}
	}
	q->next = NULL;
	s->next = NULL;
    printf("奇数项输出为:");
    output2(l2);
    printf("偶数项输出为:");
    output2(l3);
}
//求俩个单增有序单链表L1 L2的公共元素 放入新的单链表中
void  interset(linklist *A,linklist *B, linklist *c)
{
    linklist *pa,*pb,*pc,*u;
    c=(linklist*)malloc(sizeof(linklist));
    c->next=NULL;
    pc=c;
    pa=A;
    pb=B;
    while(pa!=NULL&&pb!=NULL)
    {
        if(pa->data<pb->data)
        pa=pa->next;
        else if  (pa->data>pb->data)
        {
        pb=pb->next;
        }
        else
        {
         u=(linklist*)malloc(sizeof(linklist));
         u->data=pa->data;
         u->next=NULL;//方便作为尾结点插入
         pc->next=u;
         pc=u;
         pa=pa->next;
         pb=pb->next;
        }
    }
    printf("交集");
    output2(c);
}
    

//删除链表中重复的元素 要求性能最好
linklist *DeleteSame(linklist *L) 
{
    linklist *p = L,*q=p;
	if (L == NULL||L->next==NULL)
    return L;
	while (p)
	 {
		q = p->next;//当前元素和相邻元素
		 if (q && (p->data == q->data))
         {
			 p->next = q->next;
			 free(q);
		 }
		 else
          p = p->next;
	 }
	output(L);

  }
//递增有序顺序表 不申请新节点 使得合并后成为一个新集合 合并后用L1的头节点作为头节点 删除L2的头节点
void unionset(linklist *a,linklist *b)
{
    linklist *pa,*pb,*u,*R;
    pa=a;//pa指向头节点 为了a表的插入处理
    pb=b;
    while(pa->next!=NULL&&pb->next!=NULL)
    {
        if(pa->data<pb->data)
        pa=pa->next;
        else if(pa->data>pb->data)
        {
            u=(linklist*)malloc(sizeof(linklist));
            u->data=pb->data;
            u->next=pa->next;
            pa->next=u;
            pb=pb->next;
        }
       else
       {
           pa=pa->next;
           pb=pb->next;
       }
    }
    if(pa->next==NULL)
    {
       if(pa->data==pb->data)
       pa->next=pb->next;
       else
       pa->next=pb;
    }
    if(pb->next==NULL)
    {
        while(pa->next !=NULL)
        {
            pa=pa->next;
        }
       if(pa->data==pb->data)
       pa->next=pb->next;
       else
       pa->next=pb;
        
    }

    output(a);
}

主函数

#include"linkList.h"
#include 
#include 
#include  
int main()
{
  linklist *L;
  linklist *a;
  linklist *b;
  linklist *c;
  linklist *L7;
  linklist *L8;
	int n;
  int i;
	int x;
   do
    {
		printf("请选择你想要实现的功能\n");
		printf("-------1.尾插法创建链表 打印创建结果----------------\n");
		printf("-------2.头插法创建链表  打印创建结果---------------\n");
		printf("-------3.销毁单链表----------------------------------\n");
		printf("-------4.求链表长度---------------------------------\n");
		printf("-------5.求链表中第i个元素------------------------\n");
		printf("-------6.在i个结点前插入值为x的结点--------------\n");
		printf("-------7.查找元素值为x的结点 成功返回结点指针-------\n");
    printf("-------8.删除单链表中的第i个元素结点-----------------\n");
    printf("-------9.在单增有序的单链表中插入值为x的元素-----------\n");
    printf("-------10.将单链表中的奇数项和偶数项分开 将原表和新表同时输出-\n");
    printf("-------11.求两个单增有序单链表的交集 放入新的单链表--\n");
    printf("-------12.删除单链表中的重复元素-------------------------\n");
    printf("-------13.将两个单增有序单链表合并,使得合并后成为一个集合--\n");
    scanf("%d",&n);
    switch(n)
		{
            case 1:
            system("CLS");
            L=CreateList_End();
            system("Pause");
            break;

            case 2:
            system("CLS");
            L=CreateList_Front();
            system("Pause");
            break;

            case 3:
            system("CLS");
            ReleaseLiList(L);
            system("Pause");
            break;

             case 4:
            system("CLS");
            Length (L);
            system("Pause");
            break;

             case 5:
            system("CLS");
            printf("请输入你想要查找的元素");
            scanf("%d",&i);
            finddata(L,i);
            system("Pause");
            break;
             case 6:
            system("CLS");
            printf("请输入你想要插入元素的位置");
            scanf("%d",&i);
            printf("请输入你想插入元素的大小");
            scanf("%d",&x);
            interdata(L,i,x);
            system("Pause");
            break;
             case 7:
            system("CLS");
            printf("请输入你想要查找元素的大小");
            scanf("%d",&x);
            listfind(L,x);
            system("Pause");
            break;
             case 8:
            system("CLS");
            printf("请输入你想要删除元素的位置");
            scanf("%d",&i);
            deletedata(L,i);
            system("Pause");
            break;
             case 9:
            system("CLS");
            printf("请输入你想要插入元素的大小");
            scanf("%d",&x);
            inclinklist(L,x);
            system("Pause");
            break;
             case 10:
            system("CLS");
            splitlinklist(L);

            system("Pause");
            break;

            case 11:
            system("CLS");
            a=CreateList_End();
            b=CreateList_End();
            interset(a,b,c);
            system("Pause");
            break;
             case 12:
            system("CLS");
            DeleteSame(L);
            system("Pause");
            break;
             case 13:
            system("CLS");
            
            L7=CreateList_End();
            L8=CreateList_End();
            unionset(L7,L8);
            system("Pause");
            break;
        default:
			printf("Selection is error!\n");
			system("Pause");
        }
	} while (1);
  return 0;
}

你可能感兴趣的:(数据结构,算法)