对struct的熟练运用和链表

 选夫婿^_^ 

这一题要注意的是先全部都排好序,然后再选出合格人来,会好做很多

输入格式:

潘小姐给你了所有报名男生的信息。输入数据的第一行是一个正整数N(0 < N < 1000)。然后N行数据,每行包含三部分,用空格隔开。第一部分是报名者的姓名name(长度小于20的字符串),然后是整数身高h(0 < h < 300),第三部分是整数体重w (0 < w < 200)。

最后一行是四个整数a,b,c,d.表示身高的合格范围是[a,b],体重的合格范围是[c,d](0 < a < b < 200, 0 < c < d < 300)。

输出格式:

你需要把合格的男生信息按照身高从低到高输出,格式跟输入一样,也是每行三个信息,共N行,如果身高相同则按体重从轻到重输出,如果身高相同并且体重相同则按照输入顺序依次输出,若没有合格人选则输出NO,具体格式见样例。

输入样例:

8
武大郎 70 40
西门庆 180 70
李逵 160 150
燕青 175 69
鲁智深 180 100
武松 180 75
小泉纯一狼 30 20
孙二娘 169 60
165 190 60 90

输出样例:

孙二娘 169 60
燕青 175 69
西门庆 180 70
武松 180 75

代码如下 

#include<stdio.h>
#include<math.h>
#include<string.h>
struct man{
	char name[20];
	int h;
	int w;
};
int main()
{
	struct man a[2000],t;
	int n,h1,h2,w1,w2,m=0;
	scanf("%d",&n);
	for(int i=0;i<n;i++){
		scanf("%s %d %d",a[i].name ,&a[i].h ,&a[i].w );   //输入
	}
	scanf("%d %d %d %d",&h1,&h2,&w1,&w2);
	for(int i=0;i<n-1;i++){
		for(int j=0;j<n-1-i;j++){
			if(a[j+1].h<a[j].h){
				t=a[j+1];
				a[j+1]=a[j];
				a[j]=t;
			}
			else if(a[j+1].h==a[j].h){   //如果身高一致,则排好体重
				if(a[j+1].w<a[j].w){
					t=a[j+1];
					a[j+1]=a[j];
					a[j]=t;
				}
			}
		}
	}
	for(int i=0;i<n;i++){     //先总的排好序,再选出合格的标准
		if(a[i].h<=h2&&a[i].h>=h1&&a[i].w>=w1&&a[i].w<=w2){
			m++;   //计数
			printf("%s %d %d\n",a[i].name ,a[i].h ,a[i].w );
		}
	}
	if(m==0)
		printf("NO\n");
	
}

 阅览室 

这一题主要是对书的借用和归还要标记清楚,我才用的是数组来标记,借用和归还,还要判断是否为同一本书

天梯图书阅览室请你编写一个简单的图书借阅统计程序。当读者借书时,管理员输入书号并按下S键,程序开始计时;当读者还书时,管理员输入书号并按下E键,程序结束计时。书号为不超过1000的正整数。当管理员将0作为书号输入时,表示一天工作结束,你的程序应输出当天的读者借书次数和平均阅读时间。

注意:由于线路偶尔会有故障,可能出现不完整的纪录,即只有S没有E,或者只有E没有S的纪录,系统应能自动忽略这种无效纪录。另外,题目保证书号是书的唯一标识,同一本书在任何时间区间内只可能被一位读者借阅。

输入格式:

输入在第一行给出一个正整数N(≤10),随后给出N天的纪录。每天的纪录由若干次借阅操作组成,每次操作占一行,格式为:

书号([1, 1000]内的整数) 键值SE) 发生时间hh:mm,其中hh是[0,23]内的整数,mm是[0, 59]内整数)

每一天的纪录保证按时间递增的顺序给出。

输出格式:

对每天的纪录,在一行中输出当天的读者借书次数和平均阅读时间(以分钟为单位的精确到个位的整数时间)。

输入样例:

3
1 S 08:10
2 S 08:35
1 E 10:00
2 E 13:16
0 S 17:00
0 S 17:00
3 E 08:10
1 S 08:20
2 S 09:00
1 E 09:20
0 E 17:00

 

输出样例:

2 196
0 0
1 60

#include<stdio.h>
#include<math.h>
#include<string.h>
int main(){
	int n;
	scanf("%d",&n);
	for(int k=0;k<n;k++){
		double  s=0;
        int hao,hh,mm,cnt=0;
        char zimu;
        int a[1010]={0},b[1010]={0},c[1010]={0};   赋初值
			while(scanf("%d %c %d:%d",&hao,&zimu,&hh,&mm),hao){
				if(zimu=='S'){
					a[hao]=2;    //标记,书已经借走
					b[hao]=hh*60+mm*1;   //算时间
				}
				else if(a[hao]==2){    //若为同一本书
						c[hao]=hh*60+mm*1;   
						s=s+(c[hao]-b[hao]);
						a[hao]=0;   //表示书已经归还
						cnt++;    //标记
				}
            }
				if(cnt!=0){
					s=s/cnt;   //算平均时间
				}
				printf("%d %d\n",cnt,(int)(s+0.5));
    }
} 

单链表基本操作

插入:主要是先找到那个节点的位置上,如何找呢,用cnt来标记个数,循坏一次cnt++,因此就找到那个节点的位置,就退出循环,把链表链接上去

删去:其实和插入差不多,也是用cnt来计数,值得注意的是,要找到那个删去的节点,先找的它的前一个节点,因为单链表,不像双链表那样可以pre,找到前一个节点,所以就只能先找到它的前一个节点,就让  p->next=p->next->next;直接相当于跳过了那个要删去的节点

还有一点要特别注意,你插入和删除了节点,你的节点数也会跟着改变,当你想要再一次插入后删除时,节点的位置就不一样了,我才用的是n++和n--,来处理这个问题

这次我才用的c++语言,算是第一次用吧,感觉还可以,希望以后可以更好

请编写程序实现单链表插入、删除结点等基本算法。给定一个单链表和一系列插入、删除结点的操作序列,输出实施上述操作后的链表。单链表数据域值为整数。

输入格式:

输入第1行为1个正整数n,表示当前单链表长度;第2行为n个空格间隔的整数,为该链表n个元素的数据域值。第3行为1个正整数m,表示对该链表施加的操作数量;接下来m行,每行表示一个操作,为2个或3个整数,格式为0 k d或1 k。0 k d表示在链表第k个结点后插入一个数据域值为d的结点,若k=0则表示表头插入。1 k表示删除链表中第k个结点,此时k不能为0。注:操作序列中若含有不合法的操作(如在长度为5的链表中删除第8个结点、删除第0个结点等),则忽略该操作。n和m不超过100000。

输出格式:

输出为一行整数,表示实施上述m个操作后的链表,每个整数后一个空格。输入数据保证结果链表不空。

输入样例:

5
1 2 3 4 5
5
0 2 8
0 9 6
0 0 7
1 0 
1 6

输出样例:

7 1 2 8 3 5 

 

#include <bits/stdc++.h>
using namespace std;
typedef struct node{
	int data;
	struct node* next;
}node;
node* creatlink(int n){    //创建链表,连起来
	node* head =new node;
	node* p=head;      //p来代替头结点
	head->next =NULL;    //相当于初始化
	for(int i=0;i<n;i++){
		node *q=new node;
        q->next = NULL;
		cin>>q->data;
		p->next =q;
		p=p->next ;
	}
    return head;
}
void display(node *head){   //输出链表
	node *p=head->next;
	while(p!=NULL){
		cout<<p->data<<" ";    //控制格式的输出
		p=p->next ;
	}
    printf("\n");
}
void deletelink(int k,node *head){   //删除
	int cnt=0;
	node *p=head;
	while(1){
		if(cnt==k-1)   //找到要删除的前面那个节点
		break;
		cnt++;
		p=p->next;
	} 
	p->next =p->next->next;   //链接链表
}
void charulink(int k,int d,node *head){  //插入
	node *p=head;
	int cnt=0;
	if(k==0){   输入0是单独考虑
			node*r=new node;
			r->data =d;
			r->next =head->next;
			head->next =r;
	}
	else{
		while(1){ 
			if(cnt==k)
			break;
			cnt++;
			p=p->next;
		}	
	node *r=new node;
	r->data =d;
	r->next =p->next;
	p->next =r;
	}
}
void shuru(int n, node *head){  //输入
	int m,o,k,d,cnt=0;
	cin>>m;
	while(m--)
    {
        cin>>o;
			if(o==1){
				cin>>k;
			    if(k!=0&&k<=n){
				    deletelink(k,head);
                    n--;   //节点减少
			    }
		    }
			else if(o==0){
				cin>>k>>d;
			    if(k<=n){
				    charulink(k,d,head);   
                    n++;   //节点增加
			    }
		    }
	    }
} 
int main(){  主函数
	node *head;
	int n;
	cin>>n;
	head=creatlink(n);
	shuru(n,head);   //注意这里要把head也传进去,不然就会段错误了,我可找了好久
	display(head);
} 

 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值