自考本科-算法设计题(持续更新)


本文章代码全为伪代码

线性表

线性表包含顺序表和链表,链表包含单链表、循环链表、双向链表

顺序表的基本运算

插入运算

注释:
结构体成员的引用

  • 箭头(->):左边必须为指针
  • 点(.):左边必须为实体
// L为结构体的指针,i为在第i个位置之前插入元素,x为插入的元素
void InsertList(SeqList *L, int i, DataType x)
{
	int j;	// 表L最后一个元素索引位
	//判断插入位置是否小于1或者大于最后一位+1
	if(i<1 || i>L->length+1){
		printf("position error")
		return;
	}
	// 判断表是否已满
	if(L->length>=ListSize){
		printf("overflow")
		return;
	}
	for(j=L->length-1;j>=i-1;j--){
		L->data[j+1]=L->data[j];	//将i位之后元素,逐一后移
	}
	L->data[i-1]=x;		//将x插入第i位
	L->Length++;		//列表长度+1
}

删除运算

//L为结构体指针,i为删除i位置的元素
viod DeleteList(SeqList *L, int i){
	int j;		//j为删除元素的下标
	DataType x;	//定义需要删除的元素

	if(i<1 || i>L-Length){
		printf("position error");
		return;
	}
	// 从第i位后元素开始,依次加前移
	for(j=i-1;j<=L->Length-1;j++){
		L->data[j]=L->data[j+1];
	}
	L->Length--;
	return x;
}

顺序表综合使用

试写一算法,实现在顺序表中找出最大值和最小值的元素及其所在的位置
// 使用4个变量分别记录,最大值、最小值以及最大值位置和最小值位置
void MaxMin(SeqList L, DataType *max, DataType *min, int *k, int *j)
{
	int i;	//i初始值为1,第0位指针元素无需判断	
	*max=L.data[0];
	*min=L.data[0];
	*k=*j=1;	//初始化第一个元素为最大值和最小值
	for(i=1;i<L.length;i++){
		if(L.data[i]>*max){
			*max=L.data[i];
			*k=i;
		}
		else if(L.data[i]<*min){
			*min=L.data[i];*j=i
		}
	}
	
	
}
已知一个长度为n的顺序存储的线性表,试写一算法将该线性表逆置

思路:a,b值互换,需要一个中间变量x,x=a,a=b,b=x

SeqList Converts(SeqList L)
{
	DataType x;		//模糊定义一个x数据类型变量,用来存储逆序时的值
	int i,k;		//i为顺序表的下标,k为顺序表长度的一半
	k=L.length/2;
	for(i=0;i<k;i++){
		L.data[i]=L.data[L.length-i-1]
		L.data[L.length-i-1]=x;
	}
	return L;
}
假设有两个线性表LA和LB分别表示两个集合A和B,现要求一个新的集合A=A∪B(集合的并)

思路:在LB中循环得出值x,判断x是否在LA中,不存在则添加到LA中

void union(Linner_List LA,Linner_List LB)
{
	n=ListLength(LA);
	int i;			//i为LB的下标
	DataType x;		//模糊定义x的数据类型
	for(i=0;i<=List;i++){
		x=GetNode(LB,i);	//获取线性表LB中下标为i的值
		if(LocateNode(LA,x)==0)		//获取x值在LA中的位置,若为0表示不存在
			InsertList(LA,++n,x);	//在LA的N+1位置插入x
	}
}
删除线性表L中重复的元素

思路:从表L的第一个元素(i=1)开始,逐个检查i位置后的任意一位j,若两值相同,则从L表中移除,直到L表的最后一位为止。

void  purge(Linera_List L)
{
	int i,j;
	DataType x,y;
	i=1;
	while(i<=ListLength(L)){	//注意,此处L表的长度只能动态获取,不能提前获取
		x=GetNode(L,i);
		j=i+1;
		// 逐个判断i后每位值是否与i相同
		while(j<=ListLength(L)){	//注意,此处L表的长度只能动态获取,不能提前获取
			y=GetNode(L,j);
			if(x==y){
				DeleteList(L,j);}
			else
				j++;
		}
	}
}

单链表的基本运算

建立单链表

头插法建表

头插法建表是从一个空表开始,重复读入数据,生成新的节点,将读入的数据存放到新节点的数据域中,然后将新节点插入到当前链表的表头上,知道读入结束标志为止。
:在空链表head中依次插入数据域分别为a、b、c的节点之后,将x为数据域的新结点p插入到当前链表表头,其指针的修改变化如下图
在这里插入图片描述

LinkList CreateListF()
{
	LinkList head;		//链表的首个元素的指针
	ListNode *p;		//p 为需要插入元素的指针
	char ch;			//需要插入的元素
	head=NULL;			//置空链表
	ch=getchar();		//获取第一个元素(伪代码)
	while(ch!='\n'){
		p=(ListNode *)malloc(sizeof(ListNode));		//申请新的节点,动态扩容
		p->data=ch;
		p->next=head;
		head=p;
		ch=getchar();	//获取下一个元素
	}
	return head;	//返回链表的头指针
}
尾插发建表

为了方便操作,引入头结点

// 尾插法建立带头结点的单链表算法
Link CreatListR()
{
	LinkList head=(ListNode *)malloc(sizeof(ListNode));		// 申请头结点
	ListNode *p,*r;		// p 为插入元素指针,r为尾指针
	DataType ch;
	r=head;				// 将尾指针指向头结点,此时链表为空
	while((ch = getchar())!='\n'){
		p=(ListNode *)malloc(sizeof(ListNode));		//申请新节点
		p->data=ch;
		r->next=p;	// 将新添加的元素,连接到链表,插入第一个元素时,等价于head->next=p
		r=p;		// 将尾指针指向尾节点
	}
	r->next=NULL;	// 循环结束后,将尾指针置空
	return head;	// 返回链表的头结点
}

查找运算(带头结点),返回内存地址

按节点序号查找

序号为0是头结点

// head为带头结点的单链表的头指针,i为要查找的节点序号
// 若查找成功,则返回查找节点的存储地址,否则返回NULL
ListNode * GetNodei(LinkList head, int i)
{
	// 指针p为节点的指针,j为节点的序号
	ListNode *p; int j;
	p=head->next; j=1;		// 将p指向head, j置为1
	while(p&&j<i){			// 当p为NULL或循环到第j位为止
		p=p->next;	++j		// 将p指针指向下一个节点
	}
	if(j=i){
		return p;			// 返回查找节点的内存地址
	}
	else{return NULL;}
}
按节点值查找
// head 为带头结点的单链表的头指针,k为要查找的节点的值
// 查找成功返回存储节点内存地址,失败返回NULL
ListNode * LocateNodek(LinkList head, DataType k)
{
	ListNode *p;
	p=head->next;
	while(p&&p->data!=k){	// 当p非空和值不为k时执行
		p=p->next;			// 指针指向下一个节点
	}
	return p;				// 返回查找节点的内存地址
}

插入运算

void InsertNode(LinkList head, int i, DataType x)
{
	ListNode *p; int j;
	p=head;
	j=0;	//0号节点为头结点
	
	while(p&&j<i-1){
		p=p->next;	// 指向下一个节点
		++j;
	}
	if(p==NUll){
		printf("error\n");return
	}
	else{
		s=(ListNode *)malloc(sizeof(ListNode));		//申请新节点
		s->data=x;		// x为插入节点的数值域
		s->next=p->next;
		p->next=s;
	}
}

删除运算

将单链表的第i个节点删除,并返回节点的值

DataType DeleteList(LinkList head,int i){
	// 在以head为头指针的带头结点的单链表中删除第i个节点
	ListNode *p, *s;		// p为循环节点的指针,s为删除节点的指针	i-1 对应的p,i对应的s
	DataType x;int j;		// x为删除节点的返回值 x=s->data, j为节点位置,从0开始,0对应头结点
	p=head; j=0;			// p指向头结点
	while(p!=NULL && j<i-1){
		p=p->next;			// 循环节点后移
		++j;
	}
	if(p==NULL){
		printf("位置有误\n");
		exit(0);
	}
	else{
		s=p->next;			//s对应循环节点p的下一个节点
		p->next=s->next;
		x=s->data
		free(s);
		return(x)
	}
}

单链表的运算枚举

分离单链表的奇偶位元素
  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值