201709-2公共钥匙盒

一、原题

问题描述
试题编号: 201709-2
试题名称: 公共钥匙盒
时间限制: 1.0s
内存限制: 256.0MB
问题描述:
问题描述
  有一个学校的老师共用 N个教室,按照规定,所有的钥匙都必须放在公共钥匙盒里,老师不能带钥匙回家。每次老师上课前,都从公共钥匙盒里找到自己上课的教室的钥匙去开门,上完课后,再将钥匙放回到钥匙盒中。
  钥匙盒一共有 N个挂钩,从左到右排成一排,用来挂 N个教室的钥匙。一串钥匙没有固定的悬挂位置,但钥匙上有标识,所以老师们不会弄混钥匙。
  每次取钥匙的时候,老师们都会找到自己所需要的钥匙将其取走,而不会移动其他钥匙。每次还钥匙的时候,还钥匙的老师会找到最左边的空的挂钩,将钥匙挂在这个挂钩上。如果有多位老师还钥匙,则他们按钥匙编号从小到大的顺序还。如果同一时刻既有老师还钥匙又有老师取钥匙,则老师们会先将钥匙全还回去再取出。
  今天开始的时候钥匙是按编号从小到大的顺序放在钥匙盒里的。有 K位老师要上课,给出每位老师所需要的钥匙、开始上课的时间和上课的时长,假设下课时间就是还钥匙时间,请问最终钥匙盒里面钥匙的顺序是怎样的?
输入格式
  输入的第一行包含两个整数 NK
  接下来 K行,每行三个整数 wsc,分别表示一位老师要使用的钥匙编号、开始上课的时间和上课的时长。可能有多位老师使用同一把钥匙,但是老师使用钥匙的时间不会重叠。
  保证输入数据满足输入格式,你不用检查数据合法性。
输出格式
  输出一行,包含 N个整数,相邻整数间用一个空格分隔,依次表示每个挂钩上挂的钥匙编号。
样例输入
5 2
4 3 3
2 2 7
样例输出
1 4 3 2 5
样例说明
  第一位老师从时刻3开始使用4号教室的钥匙,使用3单位时间,所以在时刻6还钥匙。第二位老师从时刻2开始使用钥匙,使用7单位时间,所以在时刻9还钥匙。
  每个关键时刻后的钥匙状态如下(X表示空):
  时刻2后为1X345;
  时刻3后为1X3X5;
  时刻6后为143X5;
  时刻9后为14325。
样例输入
5 7
1 1 14
3 3 12
1 15 12
2 7 20
3 18 12
4 21 19
5 30 9
样例输出
1 2 3 5 4
评测用例规模与约定
  对于30%的评测用例,1 ≤  NK ≤ 10, 1 ≤  w ≤  N, 1 ≤  sc ≤ 30;
  对于60%的评测用例,1 ≤  NK ≤ 50,1 ≤  w ≤  N,1 ≤  s ≤ 300,1 ≤  c ≤ 50;
  对于所有评测用例,1 ≤  NK ≤ 1000,1 ≤  w ≤  N,1 ≤  s ≤ 10000,1 ≤  c ≤ 100。


二、分析

这是一道签到题。Jardon吗,签什么玩意签了2小时。下面我会详细说明各种错误,这题是我当时考试CCF时的一道题目,记得很轻松就拿了100,不像今天这么累两个小时才A过的。待我分析


第一次编译错误,因为a.st<b.st,我增加了一个类型,改了类型名,结果这个地方没能一起改过变量名;而且我的输出没有用空格分开!!

第二次编译错误,我改成了a.t<b.t,然后我手贱看着struct EVE{}EVE;不顺眼,就把改成了struct eve{}EVE;呵呵,和后边变量名重名了。

第三次编译错误,其实第二次已经发现那一块不对劲的地方了,是的,没错,就是没加typedef!!;而且我的eve赋值时写的居然是i而不是2*i。

第四次错误,起始这里已经得到一些分了,这些分就是仅仅按照时间排序的20分。是的,没错,我眼缺,没看到题目条件要求同时出现的情况。且看我接下来怎么晕头转向的乱改代码。

四->五,我把cmp里面的<改成了>,,真奇葩,没把题目条件记下来就开始乱怀疑,居然怀疑自己对cmp的用法而不是怀疑自己是不是没记全条件,上一道题目也是这样的。0分。

五->六,我又改成了>,然后查了查cmp返回值,。。。改了改cmp返回值,坑啊

六->七,难道是我格式不正确?改了改,最后一个数不带空格。奥,对了,还有一个人还书,一个人借书的情况,于是加上了这个cmp判断,又得到20分。

七->八,嗯??我怎么又错了,我改了什么?我放到编译器里,很明显第二个样例不对,嗯我漏了条件加上了啊?那个同时还书的情况我没考虑,嗯,cmp得再加一层判断。

八->九,条件判断==0和==1写反了,改改就行了。

所以,为什么我最后对了呢。。因为最后改第八遍的时候,我实在受不了了,开了编译器,跑了跑样例,明显第二个不对,于是意识到肯定还有个那个同时还书的条件。

综上所述,加上前一道2号题目的经验,2号题目和1号题目相比,没有难度的质的提升,就是题目很长,容易让人就不住题目说了什么,因此一开始多花时间在读题建立自己的思维模型上,想不全不做 ,就不会像我这么傻的胡乱改,浪费2个小时。毕竟CCF只有3个小时时间。第一题也是如此。而后三道题目,难点就不是读题目后容易忘了了,而是(1)没有足够的模型准备(2)因为没有模型准备,所以不知道怎么作,读不懂题目想让干啥。

因此总结:

第一题,难点,想的太多,那些不会用过没有超过20次或者不理解透彻,张口出代码,下笔成代码的就不要用那种算法,这个题目肯定是P的,多项式套最多两到三层循环,循环里面写全判断条件就能满分,千万别想多。

第二题,抽象记忆力要好,一定得花足够多时间在读题目上,这个题肯定也是P的,但是表述和判断会比第一题复杂的多,还有就是可能会要求一些基本功,比如algorithm文件,排序函数sort等。此后再表。且看我刷第三个2题,千万不能再犯这种读题没想明白没看全导致自己胡乱改了。下面是写炸后的代码:

#include <iostream>
#include <algorithm>
#define MAX 1000
#define ALL 2000
using namespace std;
typedef struct rend{
int no;
int st;
int cost;
}RendEve;
typedef struct EVET{
int no;
int t;
int isr;
}EVE;
bool cmp(EVE a,EVE b){
if(a.t>b.t)return false;
else if(a.t==b.t){
if(a.isr==1&&b.isr==0){
return false;
}else if(a.isr==0&&b.isr==0){
    return a.no<b.no;
}
}
return true;
}
int main(){
int n,k;
cin>>n>>k;
int i,j;
RendEve arr[MAX]={};
//read raw data
for(i=0;i<k;i++){
cin>>arr[i].no>>arr[i].st>>arr[i].cost;
}
EVE eve[ALL]={};
//get all event
for(i=0;i<k;i++){
eve[2*i].no=arr[i].no;eve[2*i].t=arr[i].st;eve[2*i].isr=1;
eve[2*i+1].no=arr[i].no;eve[2*i+1].t=arr[i].st+arr[i].cost;eve[2*i+1].isr=0;
}
// sort event
sort(eve,eve+2*k,cmp);
//init box
int box[MAX]={};
for(i=0;i<n;i++){
box[i]=i+1;
}
//process event
for(i=0;i<2*k;i++){
if(eve[i].isr==1){
for(j=0;j<n;j++){
if(box[j]==eve[i].no){
box[j]=0;break;
}
}
}else{
for(j=0;j<n;j++){
if(box[j]==0){
box[j]=eve[i].no;break;
}
}
}
}
for(i=0;i<n-1;i++){
cout<<box[i]<<" ";
}
cout<<box[n-1];
return 0;
}


猜你喜欢

转载自blog.csdn.net/SiKongPop/article/details/79792696
今日推荐