数据结构 1-2 单链表 例题

单链表

题目:
在这里插入图片描述

代码片段:

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
 
// 定义符号常量
#define LIST_INIT_SIZE 50
#define LISTINCREMENT 10
#define OK 1
#define ERROR 0
#define OVERFLOW -2
// 定义元素类型
typedef int ElemType;
typedef int Status;
/* 单链表类型定义 */
typedef int LElemType_L;

/* 单链表结构体 */
typedef struct LNode
{
	LElemType_L data;
	struct LNode* next;
}LNode;
typedef LNode* LinkList;		//指向单链表结点的指针 


//初始化链表 
Status InitList_L(LinkList *L)		
{
	(*L) = (LinkList)malloc(sizeof(LNode));
	if(!(*L))
		exit(OVERFLOW);
	(*L)->next = NULL;
	
	return OK;
}

//在L表的第i个位置插入e 
Status ListInsert_L(LinkList L, int i, LElemType_L e){
	LinkList p, s;
	int j;
	
	p = L;
	j = 0; 
	
	while(p && j<i-1)					//寻找第i-1个结点 
	{
		p = p->next;
		++j;
	}
	
	if(!p || j>i-1)
		return ERROR;

	s = (LinkList)malloc(sizeof(LNode));	//为s申请空间 
	if(!s)
		exit(OVERFLOW);
	s->data = e;
	s->next = p->next;
	p->next = s;

	return OK;
}

//求表长 
int ListLength_L(LinkList L)
{
	LinkList p;
	int i;
	
	if(L)
	{
		i = 0;
		p = L->next;
		while(p)
		{
			i++;
			p = p->next;
		}		
	}
	
	return i;
}


//主要的函数 
Status changelist(LinkList &L1,LinkList &L2)	//主要运用前插法,二者最小插在L3前面,随着越来越大的数插在L3前面,这样L3最后也会变成递减链表。 
{
	LinkList L3;
	LinkList p1 = L1->next;
	LinkList p2 = L2->next;
	LinkList p3;
	L3 = p3 = L1;
	p3->next = NULL;
	
	LinkList p4;
	
	while(p1&&p2)		//只有p1和p2都非空时候 
	{	
		if(p1->data <= p2->data)		//把p1的这个结点插入到p3去 
		{	
			p4=p1;		//用p4指向这时候的p1,因为下一步就要让L1中删除这个p1,如果没有记下,直接就丢失了这个结点  
			p1= p1->next;		//在L1中 头指针指向下一个,即删除这个结点 
			p4->next=p3->next;		//之前把那个结点保存了下来,再让这个结点指向L3里面的第一个结点,即后面接上去 
			p3->next= p4;		//再让L3的头结点接上这个结点,完成结点的插入 
		} 
		else
		{	p4=p2;
			p2= p2->next;
			p4->next=p3->next;
			p3->next= p4;
		}
	} 
	
	if(!p1)			//如果p1是空的,!p1就是1 ,执行这段语句 。 
		p1=p2;			//反正把p2余下的全部接在p1后面,后面方便操作; 如果p1不空,那p2必是空的,依旧继续。 
		
	while(p1!=NULL)		//p1非空,经过上面的if判断,防止上面p1和p2都为空时候依旧继续操作了,也就是排除了p1==p2==NULL; 
	{	
			p4=p1;
			p1= p1->next;
			p4->next=p3->next;
			p3->next= p4;
	} 
	delete L2;		//删除L2 因为是空链表 
	
	L1=p3;			//把p3重新还给L1 
	return OK;
}


void Visit(LElemType_L x)
{
	printf("%d ",x);	
}
//遍历并输出链表的全部内容 
Status ListTraverse_L(LinkList L)
{
	LinkList p;

	if(!L)
		return ERROR;
	else
		p = L->next;	

	while(p)
	{
		Visit(p->data);
		p = p->next;
	}
	printf("\n");
	return OK;
}



int main() {
	LinkList L1,L2;
    InitList_L(&L1);
	InitList_L(&L2); 
	
	for(int i=0;i<=20;i++)
	{
		ListInsert_L(L1, i,i*2);
		ListInsert_L(L2, i,i*3);
	}
	ListTraverse_L(L1);
	ListTraverse_L(L2);	
	
	changelist(L1,L2);
	ListTraverse_L(L1);
    return 0;
}

实验结果:
在这里插入图片描述

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值