(一)
程序功能:建立一个单向链表,头指针是list,链表中每个结点包含姓名、基本工资信息,编写一个max_list函数查找链表中最高基本工资的职工信息。要求在主函数中建立单向链表(注:当输入基本工资为0时,表示输入结束。),然后调用max_list函数查找链表中最高基本工资的职工信息,最后输出查找结果。提示:除在指定位置添加语句之外,请不要改动程序中的其他内容。
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
struct emp_node{ /*定义职工工资结点*/
char name[20]; /*姓名*/
int salary; /*基本工资*/
struct emp_node *next; /*结点指针*/
};
int size=sizeof(struct emp_node);/*结点大小*/
int main()
{
struct emp_node *list,*p1=NULL,*p2=NULL,*p=NULL;
char name[20];
int salary,n=0; /*n: 职工人数计数器*/
struct emp_node * max_list(struct emp_node *list); /*函数声明*/
/*建立新链表list*/
/**********************************************************************/
list=NULL; /*链表初始化为空表*/
/*输入若于个职工数据*/
printf("请输入职工姓名和基本工资: \n");
scanf("%s%d",name,&salary);
while(salary!=0)
{
n++; /*人数计数*/
/*申请新结点,并链入链表尾*/
p1=(struct emp_node *)malloc(size);
strcpy(p1->name,name);p1->salary=salary;p1->next=NULL;
if(n==1)list=p1; else p2->next=p1;
p2=p1;
/*输入下一个职工数据*/
scanf("%s%d",name,&salary);
}
/**********************************************************************/
/*在两条星线间填入相应代码, 调用max_list函数查找链表中最高基本工资结点*/
/**********************************************************************/
p=max_list(list);
/**********************************************************************/
/*输出查找结果*/
printf("最高基本工资的职工信息:\n");
printf("姓名:%s 基本工资:%d\n",p->name,p->salary);
return 0;
}
/*功 能:在list链表中查找最高基本工资结点 */
/*参 数:list—指针变量,指向实参链表头 */
/*返回值:返回最高基本工资结点指针 */
struct emp_node * max_list(struct emp_node *list)
{
struct emp_node *max_p; /*max_p:指向最高基本工资结点
/*在两条星线间填入相应代码, 查找链表中最高基本工资的职工信息*/
/************************************************************/
max_p=list;
while(list!=NULL)
{
if(list->salary>max_p->salary)max_p=list;
list=list->next;
}
/************************************************************/
return max_p; /*返回结果*/
}
(二)
【独立编程】程序功能:建立头指针是list 的职工单向链表,链表结点包含姓名、工资,输出链表中超过平均工资的人数。要求如下:
①定义countList()函数:统计并返回链表中超过平均工资的人数。
②定义main()函数:建立职工单向链表 list(注:工资为 0,结束输入),调用 countLisro 两数统计并返回链表中超过平均工资的人数,输出统计结果
题目要求:
(1)编程实现程序功能,然后以 pro9_2.c 为文件名保存在“第2题” 文件夹。
【提示】阅读并理解第1题的解题思路和程序,思考以下问题。
①本题采用多函数结构,包括countList0两数和main0两数。
②countlist()函数:从链表头开始,遍历链表计数链表中超过平均工资的结点个数,直 到链表结束 ③main()函数:建立职工单向链表 list,调用 countList()函数统计并返回链表中超过平均 工资的人数,输出统计结果。
(2)调试、运行程序,并给出运行结果。
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
/*定义职工工资结点*/
struct emp_node{
char name[20]; /*姓名*/
int salary; /*基本工资*/
struct emp_node *next; /*结点指针*/
};
int size=sizeof(struct emp_node);/*结点大小*/
int main()
{
struct emp_node *list,*p1=NULL,*p2=NULL,*p=NULL;
char name[20];
int salary,n=0,count,sum=0; /*n:职工人数,count:超过平均基本工资人数,sum:总工资*/
int count_list(struct emp_node *list,int avg); /*函数声明*/
/*建立新链表list*/
/*********************************************************/
list=NULL; /*链表初始化为空表*/
/*输入若干职工数据*/
printf("请输入职工姓名和基本工资: \n");
scanf("%s%d",name,&salary);
while(salary!=0)
{
/*累加总人数和总工资*/
n++;
sum=sum+salary;
/*申请新结点,并添加在链表尾*/
p1=(struct emp_node *)malloc(size);
strcpy(p1->name,name);p1->salary=salary;p1->next=NULL;
if(n==1)list=p1;else p2->next=p1;
p2=p1;
/*输入下个职工数据*/
scanf("%s%d",name,&salary);
}
/*********************************************************/
/*调用count_list函数统计链表中超过平均基本工资的人数*/
count=count_list(list,sum/n);
/*输出结果*/
printf("平均基本工资:%d\n",sum/n);
printf("超过平均基本工资的人数:%d\n",count);
return 0;
}
/*功 能:在list链表中统计超过平均基本工资的人数 */
/*参 数:list—指针变量,指向实参链表头; avg—平均基本工资 */
/*返回值:返回超过平均基本工资的人数 */
int count_list(struct emp_node *list,int avg)
{
int count; /*超过平均基本工资人数计数器*/
/*遍历链表list,统计链表中超过平均基本工资的人数*/
count=0;
while(list!=NULL)
{
if(list->salary>avg)count++;
list=list->next;
}
return count; /*返回结果*/
}
(三)
【独立编程】程序功能:建立头指针是list职工单向链表,链表结点包含姓名、工资,删除链表中指定工资的所有结点,输出删除后的链表信息。要求如下:
①定义delList()函数:删除链表中指定工资的所有结点。
2定义main()函数:建立职工单向链表list(注:工资为0,结束输入),调用delList函数删除链表中指定工资的所有结点,输出删除后的链表信息。
题目要求:
(1)编程实现程序功能,然后以pro9_3.c为文件名保存在“第3题”文件夹。
【提示】阅读并理解第1题的解题思路和程序清单,思考以下问题。
①本题采用多函数结构,包括delList()函数和main()函数。
②delList()函数:从链表头开始,遍历链表删除链表中指定工资的所有结点,直到链表结束。③main()函数:建立职工单向链表list,调用delList()函数删除链表中指定工资的所有结点,输出删除后的链表信息。
(2)调试、运行程序,并给出运行结果。
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
/*定义职工工资结点*/
struct emp_node{
char name[20]; /*姓名*/
int salary; /*基本工资*/
struct emp_node *next; /*结点指针*/
};
int size=sizeof(struct emp_node);/*结点大小*/
int main()
{
struct emp_node *list,*p1,*p2;
char name[20];
int salary,n=0;
struct emp_node * delList(struct emp_node *list,int salary); /*函数声明*/
/*建立新链表list*/
/*********************************************************/
list=NULL; /*链表初始化为空表*/
printf("请输入职工姓名和基本工资: \n");
scanf("%s%d",name,&salary);
while(salary!=0)
{
n++; /*累加人数*/
/*申请新结点,并将新结点插入链表尾*/
p1=(struct emp_node *)malloc(size);
strcpy(p1->name,name);p1->salary=salary;p1->next=NULL;
if(n==1)list=p1;
else p2->next=p1;
p2=p1;
/*输入下一个职工数据*/
scanf("%s%d",name,&salary);
}
/*********************************************************/
/*输入要删除的给定基本工资*/
printf("请输入某给定基本工资: \n");
scanf("%d",&salary);
/*调用delList函数,删除链表中等于给定基本工资的所有结点*/
list=delList(list,salary);
/*输出删除后的链表信息*/
printf("删除后的链表信息:\n");
while(list!=NULL){
printf("姓名:%s, 基本工资:%d\n",list->name,list->salary);
list=list->next;
}
return 0;
}
/*功 能:删除list链表中等于给定基本工资的所有结点 */
/*参 数:list—指针变量,指向实参链表头; salary—基本工资 */
/*返回值:返回链表头指针 */
struct emp_node * del_list(struct emp_node *list,int salary)
{
struct emp_node *p1,*p2;
if(list==NULL){ /* 链表为空链表 */
printf("空链表,无删除结点!\n");
return;
}
/* 遍历链表,删除链表中满足条件的表头结点 */
while(list!=NULL && list->salary==salary){
p2=list;
list=list->next;
free(p2);
}
/* 遍历链表,删除链表中满足要求的非表头结点 */
p1=list;p2=list->next; /* 设置p1是p2的前趋结点 */
while(p2!=NULL)
{
if(p2->salary==salary) /* p2所指结点符合删除条件 */
{
p1->next=p2->next;
free(p2);
}
else p1=p2; /* p1后移一个结点 */
p2=p1->next; /* p2指向p1的后一个结点 */
}
return list; /* 返回链表头指针 */
}
(四)
【独立编程】程序功能:建立两个按工资升序的职工单向链表list1和list2,链表结点包含姓名、工资,要求将两个链表归并成一个按工资升序排序的新链表,输出新链表信息。要求如下:
①定义mergeList()函数:将两个链表归并成一个按工资升序排序的新链表。
②定义main()函数:建立两个按工资升序的职工单向链表list1和list2(工资为0,结束输入),调用mergeList()函数将两个链表归并成一个按工资升序排序的新链表,输出新链表信息。
题目要求:
(1)编程实现程序功能,然后以pro9_4c为文件名保存在“第4题”文件夹。
【提示】阅读并理解第1题的解题思路和程序清单,思考以下问题。
①本题采用多函数结构,包括mergeList()函数和main()函数。
②mergeList()函数:将两个链表归并成一个按工资升序排序的新链表。
③main()函数:建立两个按工资升序的职工单向链表list1和list2(工资为0,结束输入)调用mergeList0函数将两个链表归并成一个按工资升序排序的新链表,输出新链表信息。
版本一
/*功能:输入若干学生成绩(输入-1为结束标志),建立两个按成绩升序的单向链表list1和list2,要求*/
/* 定义mergeList()函数,实现将两个链表拼成一个按成绩升序的新链表,输出新链表信息。 */
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
struct score_node{ /*定义学生成绩结点*/
int mark; /*成绩*/
struct score_node *next; /*结点指针*/
};
int size=sizeof(struct score_node); /*结点大小*/
int main()
{
int n,mark;
struct score_node *list1,*list2,*list,*p1,*p2;
struct score_node * mergeList(struct score_node * list1,struct score_node * list2); /* 函数声明 */
/*建立新链表list1*/
/*********************************************************/
list1=NULL; /*链表初始化为空表*/
n=1;
printf("请输入一班学生成绩: \n");
scanf("%d",&mark);
while(mark!=-1)
{
/*申请新结点并插入到链表尾*/
p1=(struct score_node *)malloc(size);
p1->mark=mark;p1->next=NULL;
if(n==1)list1=p1;
else p2->next=p1;
p2=p1;
n++;
/*输入下一个学生数据*/
scanf("%d",&mark);
}
/*********************************************************/
/*建立新链表list2*/
/*********************************************************/
list2=NULL; /*链表初始化为空表*/
n=1;
printf("请输入二班学生成绩: \n");
scanf("%d",&mark);
while(mark!=-1)
{
/*申请新结点并插入到链表尾*/
p1=(struct score_node *)malloc(size);
p1->mark=mark;p1->next=NULL;
if(n==1)list2=p1;
else p2->next=p1;
p2=p1;
n++;
/*输入下一个学生数据*/
scanf("%d",&mark);
}
/*********************************************************/
list=mergeList(list1,list2); /* 调用函数mergeList()拼接链表list1和list2 */
/* 输出拼接后的新链表list */
if(list==NULL) printf("\n拼接后的新链表是空链表!\n");
else{
printf("\n拼接后的新链表信息: \n");
while(list!=NULL){
printf("%d\n",list->mark);
list=list->next;
}
}
return 0;
}
/*功 能:拼接链表list1和list2,产生升序排列的新链表list */
/*参 数:list1、list2—指针变量,指向两个实参链表头 */
/*返回值:返回新链表头指针 */
struct score_node * mergeList(struct score_node * list1,struct score_node * list2)
{
int n;
struct score_node *list,*p1,*p2,*p,*q,*r;
/*拼接链表list1和list2,产生升序排列的新链表list*/
list=NULL; /* 新链表list初值为NULL */
p1=list1;p2=list2;n=0; /* 初始化p1和p2 */
while((p1!=NULL)&&(p2!=NULL)) /* 两链表都非空 */
{
p=(struct score_node *)malloc(size); /* 申请新结点p */
if(p1->mark<p2->mark){ /* 复制p1结点 */
p->mark=p1->mark;
p1=p1->next;
}
else{
p->mark=p2->mark; /* 复制p2结点 */
p2=p2->next;
}
/* 链入新结点p */
if(n==0)list=p;
else q->next=p;
q=p; /* 指针q指向尾结点 */
n++; /* 结点个数加1 */
}
/* 拼接未拼接完的list1或list2 */
if(p1!=NULL)r=p1;
else r=p2;
while(r!=NULL)
{
p=(struct score_node *)malloc(size);
p->mark=r->mark;p->next=NULL;
if(n==1)list=p;
else q->next=p;
q=p;
n++;
r=r->next;
}
return list; /* 返回新链表头指针list */
}
版本二
#include<stdio.h>
#include<string.h>
#include<stdlib.h>
struct student
{
char name[20]; /* 我增加的语句 */
int score;
struct student *next;
};
struct student *input()
{
struct student *head=NULL,*p1,*p2=NULL;
char name[20];
int score,n=0;
printf("输入学生的姓名和成绩(成绩为-1表示输入结束):\n");
scanf("%s%d",name,&score);
while(score!=-1)
{
n++;
if((p1=( struct student *)malloc(sizeof(struct student)))==NULL)
{
printf("无法分配储存空间.\n");
exit(0);
}
strcpy(p1->name,name);
p1->score=score;
p1->next=NULL;
if(n==1) head=p1;
else p2->next=p1;
p2=p1;
scanf("%s%d",name,&score);
}
return head;
}
struct student *merge(struct student *x, struct student *y)
{
struct student* ret=NULL,*tail=NULL,*temp=NULL;//ret始终指队头,tail始终指队尾,temp存储个体
while(x!=NULL&&y!=NULL)
{
if(x->score<y->score)
{
temp=x->next;
if(ret==NULL)
{
ret=tail=x;
ret->next=NULL;
}
else {
tail->next=x;
tail=tail->next;
tail->next=NULL;
}
x=temp;
}
else{
temp=y->next;
if(ret==NULL)
{
ret=tail=y;
ret->next=NULL;
}
else {
tail->next=y;
tail=tail->next;
tail->next=NULL;
}
y=temp;
}
}
if(x!=NULL){
tail->next=x;
}
else{
tail->next=y;
}
return ret;
}
void output( struct student *p)
{
for(;p!=NULL;p=p->next)
{
printf("%s %d\n",p->name,p->score);
}
}
void freelink( struct student *p) /* 释放链表空间 */
{
struct student *temp;
for(;p!=NULL;)
{
temp=p;
p=p->next;
free(temp); /* 释放temp结点 */
}
}
int main()
{
struct student *list1=NULL,*list2=NULL,*list=NULL;
struct student *input();
void output( struct student *p);
struct student *merge( struct student *x, struct student *y);
printf("输入俩个升序排序的链表,以成绩为-1为结束标志");
list1=input(); //得到俩个链表的队头list1和list2
list2=input();
list=merge(list1,list2);//俩个链表用归并排序合成一个升序链表并返回队头
output(list); //输出链表
freelink(list); //释放链表空间
return 0;
}
版本三
#include<stdio.h>
#include<string.h>
#include<stdlib.h>
struct student
{
char *name;
int score;
struct student *next;
};
struct student *input()
{
struct student *head=NULL,*p1,*p2=NULL;
char name[20];
int score,n=0;
printf("输入学生的姓名和成绩(成绩为-1表示输入结束):\n");
scanf("%s%d",name,&score);
while(score!=-1)
{
n++;
if((p1=( struct student *)malloc(sizeof(struct student)))==NULL)
{
printf("无法分配储存空间.\n");
exit(0);
}
p1->name=(char *)malloc(sizeof(name));
strcpy(p1->name,name);
p1->score=score;
p1->next=NULL;
if(n==1) head=p1;
else p2->next=p1;
p2=p1;
scanf("%s%d",name,&score);
}
return head;
}
struct student *merge(struct student *x, struct student *y)
{
struct student* ret=NULL,*tail=NULL,*temp=NULL;//ret始终指队头,tail始终指队尾,temp存储个体
while(x!=NULL&&y!=NULL)
{
if(x->score<y->score)
{
temp=x->next;
if(ret==NULL)
{
ret=tail=x;
ret->next=NULL;
}
else {
tail->next=x;
tail=tail->next;
tail->next=NULL;
}
x=temp;
}
else{
temp=y->next;
if(ret==NULL)
{
ret=tail=y;
ret->next=NULL;
}
else {
tail->next=y;
tail=tail->next;
tail->next=NULL;
}
y=temp;
}
}
if(x!=NULL){
tail->next=x;
}
else{
tail->next=y;
}
return ret;
}
void freelink( struct student *p) /* 释放链表空间 */
{
struct student *temp;
for(;p!=NULL;)
{
temp=p;
p=p->next;
free(temp->name); /* 释放name指向的动态空间 */
free(temp); /* 释放temp结点 */
}
}
void output( struct student *p)
{
for(;p!=NULL;p=p->next)
{
printf("%s %d\n",p->name,p->score);
}
}
int main()
{
struct student *list1=NULL,*list2=NULL,*list=NULL;
struct student *input();
void output( struct student *p);
void freelink( struct student *p);
struct student *merge( struct student *x, struct student *y);
printf("输入俩个升序排序的链表,以成绩为-1为结束标志");
list1=input();//得到俩个链表的队头list1和list2
list2=input();
list=merge(list1,list2);//俩个链表用归并排序合成一个升序链表并返回队头
output(list);//输出链表
freelink(list);
return 0;
}