【沈阳航空航天大学】 <链表-计分任务>

编程题

1. 向有序链表中插入数据并输出最大和最小值

【问题描述】输入若干按升序排列的整数,建立单向链表,后输入一个整数,把该数按原顺序插入到原链表,输出新链表中数据的最大值和最小值并输出链表中所有数据。必须用链表完成,程序中不允许有数组出现。
【输入形式】输入若干按升序排列的整数以0作为结束,和待插入的整数。用单个空格隔开。
【输出形式】输出最大值和最小值及链表中的所有数据,数据之间用单个空格隔开。
【样例输入】1 3 4 5 6 7 8 0 2
【样例输出】8 1 1 2 3 4 5 6 7 8
【评分标准】链表用完后空间要释放!

#include<stdio.h>
#include<stdlib.h>

struct Node {
	int a;
	struct Node* next;
};

struct Node* create();

int main() {
	int x, flag = 0;
	struct Node* head, * p, * o = NULL, * u = NULL;
	head = create();
	scanf("%d", &x);
	p = head;
	if (head->a > x) {
		u = (struct Node*)malloc(sizeof(struct Node*));
		u->a = x;
		u->next = head;
		head = u;
	}
	else {
		while (p != NULL) {
			if (p->a < x) {
				o = p;
				flag = 1;
			}
			p = p->next;
		}
		if (flag == 1) {
			u = (struct Node*)malloc(sizeof(struct Node*));
			u->a = x;
			u->next = o->next;
			o->next = u;
		}
		else {
			p = head;
			while (p != NULL) {
				o = p;
				p = p->next;
			}
			u = (struct Node*)malloc(sizeof(struct Node*));
			u->a = x;
			o->next = u;
			u->next = NULL;
		}
	}
	p = head;
	while (p != NULL) {
		o = p;
		p = p->next;
	}
	printf("%d ", o->a);
	printf("%d ", head->a);
	p = head;
	while (p != NULL) {
		printf("%d ", p->a);
		p = p->next;
	}
	return 0;
}

struct Node* create() {
	struct Node* head = NULL, * p1 = NULL, * p2 = NULL;
	p1 = (struct Node*)malloc(sizeof(struct Node*));
	scanf("%d", &p1->a);
	while (p1->a != 0) {
		if (head == NULL) {
			head = p1;
		}
		else {
			p2->next = p1;
		}
		p2 = p1;
		p1 = (struct Node*)malloc(sizeof(struct Node*));
		scanf("%d", &p1->a);
	}
	p2->next = NULL;
	free(p1);
	return head;
}

2. 输出单链表倒数第K个结点值

【问题描述】输入一个单向链表,输出该链表中倒数第k个结点,链表的最后一个结点是倒数第1个结点。
【输入形式】输入第一位为K值,其后接一串以空格分隔的整型值,用-1表示结束。
【输出形式】输出为倒数第K个结点的值,若无,则输出Not Found。
【样例输入】3 13 45 54 32 1 4 98 2 -1
【样例输出】4
【样例说明】K值为3,则输出链表倒数第3个结点的值为4。
【样例输入】5 13 4 -1
【样例输出】Not Found
【样例说明】K值为5,不存在倒数第5个结点,因此输出Not Found。
【评分标准】本题20分。不使用链表的不得分。

// 引入标准输入输出库和标准库  
#include <stdio.h>  
#include <stdlib.h>  

// 定义链表节点结构体  
typedef struct Node {
    int val;                 // 节点的值  
    struct Node* next;        // 指向下一个节点的指针  
} Node;

// 创建链表的函数  
Node* create() {
    Node* head = NULL;        // 头节点初始化为NULL  
    Node* tail = NULL;         // 尾节点初始化为NULL  
    int val;                   // 存储从输入读取的值  

    // 当输入的值不是-1时,继续读取和创建新节点  
    while (scanf("%d", &val) && val != -1) {
        Node* newNode = (Node*)malloc(sizeof(Node));  // 分配新节点内存  
        newNode->val = val;                           // 设置新节点的值为输入的值  
        newNode->next = NULL;                          // 新节点的下一个节点初始化为NULL  

        // 如果链表为空,则新节点为头节点和尾节点  
        if (head == NULL) {
            head = newNode;
            tail = newNode;
        }
        // 否则,将新节点添加到链表的尾部  
        else {
            tail->next = newNode;
            tail = newNode;
        }
    }
    return head;               // 返回头节点,即整个链表  
}

// 查找链表中第k个节点的值函数  
int findK(Node* head, int k) {
    // 如果链表为空或k小于等于0,则返回-1表示未找到  
    if (head == NULL || k <= 0) {
        return -1;
    }
    Node* p = head;             // 定义两个指针p和q,都初始化为头节点  
    Node* q = head;
    // 先让p指针移动k-1步,确保p指针指向第k个节点的前一个节点  
    for (int i = 0; i < k - 1; i++) {
        if (p->next != NULL) {  // 如果p的下一个节点存在,则移动p指针到下一个节点  
            p = p->next;
        }
        else {                  // 如果p的下一个节点不存在,则返回-1表示未找到第k个节点  
            return -1;
        }
    }
    // 当p指针指向第k个节点的前一个节点时,同时移动p和q指针,直到p指针到达链表的末尾  
    while (p->next != NULL) {
        p = p->next;             // p移动到下一个节点  
        q = q->next;              // q也移动到下一个节点,这样q始终指向第k个节点  
    }
    // q现在指向第k个节点,返回该节点的值  
    return q->val;               // 返回第k个节点的值  
}

int main() {
    int k;                       // 存储要查找的节点的位置k的值  
    scanf("%d", &k);              // 从标准输入读取k的值  
    Node* head = create();         // 创建链表并获取头节点指针  
    int result = findK(head, k);   // 使用findK函数查找第k个节点的值,并存储到result中  
    // 根据result的值判断是否找到第k个节点,并打印相应的消息  
    if (result == -1) {             // 如果result为-1,则表示未找到第k个节点,打印"Not Found"消息  
        printf("Not Found\n");
    }
    else {                          // 反之,打印resule值
        printf("%d\n", result);
    }
    return 0;
}

片段题

1. (指针做参数的函数定义)查找数组下标

【问题描述】从键盘输入数组元素数量 n 以及这 n 个元素;再输入 2 个数,找到这2个数在数组中的位置,即数组下标。若某个数在数组中不存在,输出 -1,注意若数组中存在多个待查找的数,要全部输出位置。
【输入形式】输入数组元素数量 n 以及这 n 个整数元素;再输入2个待查找的整数。
【输出形式】输出2个数的位置信息。

【样例输入】
3 56 85 41
27 58
【样例输出】
27 -1
58 -1

【样例输入】
4 101 25 5 444
5 101
【样例输出】
5 2
101 0

【样例输入】
6 2 6 8 8 6 8
8 6
【样例输出】
8 2 3 5
6 1 4

#include <stdio.h>
#include <stdlib.h>

int input_data(int* number);
void output_data(int* number, int n);

int main()
{
	int n, x[20];
	n = input_data(x);
	output_data(x, n);
	return 0;
}

// 定义一个函数,用于接收用户输入的数据数量并返回该数量  
int input_data(int* number) {
    int x;  // 输入数据数量  
    scanf("%d", &x);  // 读取用户输入的数量  
    for (int i = 0; i < x; i++) {
        scanf("%d", number + i);  // 循环读取x个整数并存储在数组number中  
    }
    return x;  // 返回读取的整数数量  
}

// 定义一个函数,用于输出数据和位置信息  
void output_data(int* number, int n) {
    int i = 0, x = 0, a = 0, c = 0, y = 0;  // 定义循环和条件判断变量  
    scanf("%d %d", &x, &y);  // 读取两个整数x和y  
    for (i = 0; i < n; i++) {  // 循环n次,n是数据数量  
        if (a == 0) {  // 如果还没有找到x  
            if (*(number + i) == x) {  // 如果找到x  
                printf("%d %d ", x, i);  // 输出x和位置  
                a = 1;  // 设置标志位,表示已找到x  
                continue;  // 跳过本次循环的剩余部分  
            }
        }
        else {  // 如果已经找到x  
            if (*(number + i) == x) {  // 如果再次找到x  
                printf("%d ", i);  // 输出位置  
            }
        }
    }
    if (a == 0) {  // 如果未找到x  
        printf("%d -1", x);  // 输出x和-1表示索引无效  
    }
    printf("\n");  // 换行,准备输出y的位置信息  
    for (i = 0; i < n; i++) {  // 重新开始循环n次,重复上述过程以查找和y相等的数并输出其位置信息  
        if (c == 0) {  // 如果还没有找到y  
            if (*(number + i) == y) {  // 如果找到y  
                printf("%d %d ", y, i);  // 输出y和位置  
                c = 1;  // 设置标志位,表示已找到y  
                continue;  // 跳过本次循环的剩余部分  
            }
        }
        else {  // 如果已经找到y  
            if (*(number + i) == y) {  // 如果再次找到y  
                printf("%d ", i);  // 输出位置  
            }
        }
    }
    if (c == 0) {  // 如果未找到y  
        printf("%d -1", y);  // 输出y和-1表示索引无效  
    }
}

2. (指针做参数的函数定义)规格化数据

【问题描述】输入 10 个整数,将其中最小的数与第一个数对换,把最大的数与最后一个数对换。写三个函数:
①输入 10 个数; 函数原型声明:void input_data(int *number)
②进行处理; 函数原型声明:void handle_val(int *number)
③输出 10 个数。 函数原型声明:void output_data(int *number)
【输入形式】输入 10 个整数。
【输出形式】输出对换后的10个整数。
【样例输入】10 25 6 15 87 3 26 31 85 7
【样例输出】3 25 6 15 7 10 26 31 85 87

#include <stdio.h>
#include <stdlib.h>

void input_data(int* number);
void handle_val(int* number);
void output_data(int* number);

int main()
{
	int x[10];
	input_data(x);
	handle_val(x);
	output_data(x);
	return 0;
}

// 输入10个整数到数组  
void input_data(int* number) {
    int i;
    for (i = 0; i < 10; i++) {
        scanf("%d", number + i);  // 从标准输入读取一个整数并存储到数组的当前位置  
    }
}

// 找到数组中的最大值和最小值,然后与数组的首尾元素交换  
void handle_val(int* number) {
    int i, * a, * b, t = 0;
    a = number;  // a指向数组首元素,用于寻找最大值  
    b = number;  // b指向数组首元素,用于寻找最小值  

    for (i = 0; i < 10; i++) {
        if (*a < *(number + i)) {
            a = number + i;  // 更新最大值的指针位置  
        }
    }
    for (i = 0; i < 10; i++) {
        if (*b > *(number + i)) {
            b = number + i;  // 更新最小值的指针位置  
        }
    }
    // 交换首元素与最小值  
    t = *b;
    *b = *number;
    *number = t;

    // 交换尾元素与最大值  
    t = *a;
    *a = *(number + 9);
    *(number + 9) = t;
}

// 输出数组中的所有元素  
void output_data(int* number) {
    for (int i = 0; i < 10; i++) {
        printf("%d ", *(number + i));  // 打印数组的当前元素,并在后面加一个空格  
    }
}

3. 创建并输出链表

【问题描述】从键盘输入一行字符,以 # 结束,建立链表,打印输出链表。
【输入形式】输入一行字符,以 # 结束。
【输出形式】输出 # 之前的字符串(注意空表输出情况)。
【样例输入】123456789#124
【样例输出】123456789

#include <stdio.h>    // 引入标准输入输出库(C风格)  
#include <stdlib.h>    // 引入标准库(内存分配等)  

#define LEN sizeof(Node)  // 定义Node结构体的大小  

// 使用typedef为结构体重命名,使其更易读  
typedef struct Node {
    char a;              // 存储一个字符  
    Node* next;           // 指向下一个Node的指针  
} Node;                   // 结束typedef定义  

Node* create();             // 函数声明:创建链表  
void print(Node* p);          // 函数声明:打印链表  

int main() {                  // 主函数开始  
    Node* head = NULL;          // 初始化头指针为NULL  
    head = create();            // 调用create函数创建链表并返回头指针  
    print(head);                // 打印链表  
    return 0;                   // 主函数返回0,程序结束  
}                             // 主函数结束  

Node* create() {               // 创建链表的函数开始  
    Node* head = NULL, * p1, * p2;  // 初始化头指针和两个临时指针  
    p1 = (Node*)malloc(sizeof(Node));  // 为p1分配内存并返回指向它的指针  
    scanf("%c", &p1->a);                // 从标准输入读取一个字符并存储在p1的a字段中  
    while (p1->a != '#') {               // 当读取的字符不是'#'时,继续循环  
        if (head == NULL) {              // 如果链表为空,将p1设置为头指针  
            head = p1;
        }
        else {                         // 如果链表不为空,将p1添加到链表的末尾  
            p2->next = p1;
        }
        p2 = p1;                         // 将p2移动到p1的位置,准备添加下一个节点  
        p1 = (Node*)malloc(sizeof(Node));  // 为p1分配新的内存,准备读取下一个字符  
        scanf("%c", &p1->a);                // 从标准输入读取下一个字符并存储在p1的a字段中  
    }
    return head;                       // 返回头指针,链表创建完成  
}                                   // create函数结束  

void print(Node* p) {                // 打印链表的函数开始  
    while (p != NULL) {               // 当当前节点不为空时,继续循环  
        printf("%c", p->a);             // 打印当前节点的字符字段  
        p = p->next;                  // 将指针移动到下一个节点  
    }                                // 打印链表的函数结束  
}

4. 删除链表中指定结点

【问题描述】输入链表 a,链表结点中包含学号、姓名,学号输入 -1,姓名随意代表一个链表输入结束。再输入待删除结点的学号 num,请编写删除链表中结点函数,从结点中删除学号为 num 的结点,并依次输出删除后的链表。若链表中不包含学号为 num 的结点,则先输出 no data,再依次输出链表结点。
【输入形式】输入链表 a 的数据和待删除结点的学号 num。其中,学号输入 -1,姓名随意代表一个链表输入结束。
【输出形式】输出删除后的新链表。
【样例输入】
101 Wang
102 Li
105 Zhang
106 Wei
-1 x
105
【样例输出】
101 Wang 102 Li 106 Wei
【样例输入】
101 Wang
102 Li
105 Zhang
106 Wei
-1 x
103
【样例输出】
no data 101 Wang 102 Li 105 Zhang 106 Wei

#include <iostream>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
 
#define LEN sizeof(NODE)

//用 typedef 将结构体改名字
typedef struct node {
    int num;
    char name[20];
    struct node *next;
} NODE;

NODE *Create_LinkList();
//读入学号,并删除指定学号的结点,
//成功删除返回正数,未找到学号返回负数。
int Delete_LinkList(NODE *head);
void Display_LinkList(NODE *head,int flag);
void Free_LinkList(NODE *head);

int main()
{
    NODE *head = NULL;
    int flag;
    head = Create_LinkList();//创建链表
    flag=Delete_LinkList(head);
    Display_LinkList(head,flag);//打印结果
    Free_LinkList(head);
    return 0;
}


NODE* Create_LinkList()//创建链表
{
	NODE* head, *head1, * p1, * p2;
	int n = 0;
	head1= (NODE*)malloc(LEN);
	head = NULL;
	p1 = p2 = (NODE*)malloc(LEN);
	scanf("%d %s",&p1->num,p1->name);
	while (p1->num != -1)
	{
		n += 1;
		if (n == 1)
		{
			head = p1;
		}
		else
		{
			p2->next = p1;
		}
		p2 = p1;
		p1 = (NODE*)malloc(LEN);
		scanf("%d %s", &p1->num, p1->name);
	}
	p2->next = NULL;
	head1->next = head;
	return head1;
}

int Delete_LinkList(NODE* head)//删除链表中某一个节点
{
	int x = 0;
	scanf("%d", &x);//输入需要删除的节点的数据
	NODE* p;
	p = head;
	int flag = -1;//没找到时flag为-1
	while (p->next != NULL)
	{
		if (p->next->num == x)
		{
			NODE* temp;
			temp = p->next;
			p->next = p->next->next;
			free(temp);
			flag = 1;//找到了就删除并且把flag变成1
			break;
		}
		p = p->next;
	}
	return flag;
}

void Display_LinkList(NODE *head,int flag)  //打印
{
    NODE *p;
	if(flag<0)
		printf("no data ");
    for (p = head->next; p != NULL; p = p->next)
		printf ("%d %s ", p->num,p->name);
}

void Free_LinkList(NODE *head)  //遍历释放
{
  NODE *p, *q;
  p = head;
  while (p->next != NULL)
  {
    q = p->next;
    p->next = q->next;
    free (q);
  }
  free (head);
}

5. 用指针和函数实现3个数排序

【问题描述】输入 3 个整数,按由小到大的顺序输出。指针使用部分要求定义函数 void swap(int *x, int *y),函数功能是 x 和 y 两个数互换。
【输入形式】输入 3 个整数。
【输出形式】按由小到大的顺序输出,每个数用一个空格分隔。
【样例输入】5 -1 6
【样例输出】-1 5 6

#include <stdio.h>    // 引入C标准库,用于输入输出函数如scanf和printf  
#include <stdlib.h>    // 引入C标准库,尽管这里没有用到其中的任何函数  
  
// 声明一个swap函数,用于交换两个整数的值  
void swap(int *x, int *y);  
  
int main()  // 主函数,程序的入口点  
{  
    int x, y, z;  // 定义三个整数变量x、y和z  
  
    // 从标准输入读取三个整数  
    scanf("%d%d%d", &x, &y, &z);  
  
    // 如果x大于y,调用swap函数交换它们的值  
    if (x > y)  
        swap(&x, &y);  
  
    // 如果y大于z,调用swap函数交换它们的值  
    if (y > z)  
        swap(&y, &z);  
  
    // 如果x大于y,再次调用swap函数交换它们的值。此时,x、y和z应该已经是升序排列的  
    if (x > y)  
        swap(&x, &y);  
  
    // 打印排序后的x、y和z的值  
    printf("%d %d %d", x, y, z);  
  
    return 0;  // 主函数返回0,表示程序正常结束  
}  
  
// swap函数定义,用于交换两个整数的值  
void swap(int *x, int *y)  
{  
    int t;  // 定义一个临时变量t,用于存储x的值  
  
    // 将x的值赋给t  
    t = *x;  
    // 将y的值赋给x  
    *x = *y;  
    // 将t(原来x的值)赋给y  
    *y = t;  
}

今天的内容就分享这么多
求三连!!!
求关注!!!

  • 27
    点赞
  • 23
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 1
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

NineSense

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值