这里给出两种实现方式:

(1)使用map<time, multiset<key_id> >这种结构,存储用户输入的借还钥匙的序列(multiset允许相同元素存在,且自排序)。这里的思路是,将借还时间进行统一排序(原因A:time小的先处理;原因B:同一个key出现的次数是偶数,且先出现的一定是借,后出现的是还,且不允许嵌套,或者说一个借后面一定跟着对应的还。所以我可以这么排序),思路是:map内按照time为键进行排序,对于同一时刻,借还钥匙的id按照自小到大的顺序排列。

具体执行起来,由于map是排序的,所以只要顺序的获取map中的元素,然后对value进行操作即可。

value里面也是排过序的,但是由于还钥匙要在借之前,而value里面的序列是把借还的id进行了一个总排序,我们无法分成两段,第一段是按序的还钥匙的id,第二段是借钥匙的id(借钥匙不需要排序)。所以,我们只好进行两次遍历,第一次只处理要还的钥匙,然后将这个id从value中删掉,同时更新这个钥匙的status;第二次只处理借钥匙,然后更新钥匙的status(删除不删除都无所谓)。

这里表示钥匙状态的是一个数组keyStatus,下表对应钥匙id-1,状态只有两个值,0和1,1表示待还,0表示已还或者没有被借出。借还钥匙,都要更新该钥匙对应的状态。

#include<iostream>
#include<stdio.h>
#include <set>
#include <map>
#include <stdlib.h>
using namespace std;
typedef pair<int, multiset<int> > PAIR;  int main()
{int Num_yaoshi,k_teachernum;cin>>Num_yaoshi>>k_teachernum;// Num_yaoshi=5;k_teachernum=7;int *yaoshi_pailie =new int[Num_yaoshi], *keyStatus=new int[Num_yaoshi];//初始化钥匙盒,以及每个钥匙的状态for(int i=0;i<=Num_yaoshi-1;i++){yaoshi_pailie[i]=i+1;keyStatus[i]=0;//1 means the key has been borrowed}bool flag=false;int *yaoshibianhao=new int[k_teachernum],*starttime=new int[k_teachernum],*timelong=new int[k_teachernum],*endtime=new int[k_teachernum];map<int, multiset<int> > sortedList;map<int, multiset<int> >::iterator it;multiset<int> tmpset;multiset<int>::iterator setit;//获取输入,并进行转换,然后行程键值对,放到map中for(int i=0;i<=k_teachernum-1;i++){cin>>yaoshibianhao[i]>>starttime[i]>>timelong[i];endtime[i]=starttime[i]+timelong[i];//add the yaoshibianhao[i] into map according to the starttime,按照借的时间把keyid放进去it=sortedList.find(starttime[i]);if(it==sortedList.end()){//not in the map//add the PAIR<starttime[i],multiset<yaoshibianhao[i]>> into maptmpset.clear();}else{// the time has appeared in the map, so add the yaoshibianhao[i] into the tmpsettmpset=it->second;sortedList.erase(it);}tmpset.insert(yaoshibianhao[i]);sortedList.insert(make_pair(starttime[i],tmpset));tmpset.clear();//add the yaoshibianhao[i] into map according to the endtime,按照还的时间将keyid放到map中it=sortedList.find(endtime[i]);if(it==sortedList.end()){//not in the map//add the PAIR<starttime[i],multiset<yaoshibianhao[i]>> into maptmpset.clear();}else{// the time has appeared in the map, so add the yaoshibianhao[i] into the tmpsettmpset=it->second;sortedList.erase(it);}tmpset.insert(yaoshibianhao[i]);sortedList.insert(make_pair(endtime[i],tmpset));tmpset.clear();}//test the input,测试用户的输入能否正常存储到map中
/*it = sortedList.begin();while(it != sortedList.end()){cout<<it->first<<": "<<it->second.size()<<endl;it ++;         }*///对map进行遍历,处理借还钥匙for(it = sortedList.begin();it != sortedList.end();){   tmpset.clear();tmpset=it->second;//cout<<"处理时间:"<<it->first<<", 共有:"<<tmpset.size()<<endl;int j=0;//  先处理还钥匙for(setit =tmpset.begin(); setit!=tmpset.end();){ //find the keys to be returned and return themflag=false;//printf("%d",*setit);if(keyStatus[(*setit)-1]==1) {//如果该key的状态为1,表示待还,cout<<"归还key_ "<<*setit;keyStatus[(*setit)-1]=0;//更新钥匙状态for(int i=0;i<Num_yaoshi;i++){//这个可以使用一个set来代替,就不用循环了 ,按照顺序,找到钥匙盒中的第一个空位置if(yaoshi_pailie[i]==0) {//cout<<", 放到位置"<<i+1<<endl;yaoshi_pailie[i]=(*setit);//把钥匙放到空位置tmpset.erase(setit++);//从value中删掉这个keyflag=true;break;//后面不再需要找空位置了}}if(flag==false) setit++;continue;}setit++;}//borrow key,借钥匙if(tmpset.size()>0){//防止这一时刻只有还钥匙的操作,则还过钥匙后tmpset为空,所以要判断sizefor( setit = tmpset.begin();setit!=tmpset.end();){cout<<"id= "<<(*setit)<<" ";keyStatus[(*setit)-1]=1;//更新钥匙状态for(int i=0;i<Num_yaoshi;i++){//这个可以使用一个set来代替,就不用循环了 ,找到钥匙盒中这个钥匙的位置if(yaoshi_pailie[i]==(*setit)) {yaoshi_pailie[i]=0;//钥匙盒中对应的位置置空//tmpset.erase(setit++);flag=true;break;}}setit++;//这个很重要}tmpset.clear();}it ++;         }
//输出结果for(int i=0;i<=Num_yaoshi-1;i++)cout<<yaoshi_pailie[i]<<" ";
//删除数组yaoshi_pailie=NULL;delete [] yaoshi_pailie;delete [] keyStatus;delete [] yaoshibianhao;delete [] starttime;delete [] timelong;delete [] endtime;return 0;
}

(2)使用一大堆的set来处理钥匙盒的问题,由于set是自排序的,所以这里弄了几个set来表示已经借的钥匙的集合,本时刻要还的钥匙的集合,空位置的集合。然后按照时刻从1到max_time进行遍历,对于每一个时刻,先找本时刻要还的钥匙的集合,然后还钥匙,然后再借钥匙。

#include <iostream>
#include <string>
#include <stdio.h>
#include <set>
using namespace std;int main(){int N,K,MAX_TIME=0;cin>>N>>K;int *borrowTime=new int[K],*backTime=new int[K],*keyID=new int[K], *keys=new int[N];set<int> emptyPos;//used to record the postion that is empty, items in set are sorted by defaultset<int> borrowedKeys;//used to record the keys not returnedset<int> returningKeys;//used to record the keys to returned at current timeset<int> borrowingKeys;for(int i=0;i<N;i++){keys[i]=i+1;//initializing the kyes postion at the beginning}//get the status of the keys of the dayfor(int i=0;i<K;i++){scanf("%d %d %d\n",&keyID[i],&borrowTime[i],&backTime[i]);//>>endl;backTime[i]=backTime[i]+borrowTime[i];if(backTime[i]>MAX_TIME) MAX_TIME=backTime[i];}for(int i=1;i<=MAX_TIME;i++){int backAmount=0,borrowAcount=0;for(int j=0;j<K;j++){if(backTime[j]==i){//the key will be back at this periodreturningKeys.insert(keyID[j]);//put all the keys will be back at this period into the setborrowedKeys.erase(keyID[j]);backAmount++;}if(borrowTime[j]==i){//get the keys being borrowed at this periodborrowingKeys.insert(keyID[j]);borrowedKeys.insert(keyID[j]);borrowAcount++;}}//put the sorted keys into the position specified by the sorted emptyPos if(backAmount>0){for(int k=0;k<backAmount;k++){int key=*returningKeys.begin();int pos =*emptyPos.begin();keys[pos]=key;returningKeys.erase(key);emptyPos.erase(pos);}}//remove the borrowing keys at this periodif(borrowAcount>0){for(int k=0;k<borrowAcount;k++){// can be replaced with map for(int k1=0;k1<N;k1++){int keyid=*borrowingKeys.begin();if(keys[k1]==keyid){emptyPos.insert(k1);borrowingKeys.erase(keyid);keys[k1]=0;break;}}}}borrowingKeys.clear();returningKeys.clear();}for(int s1=0;s1<N;s1++){printf("%d ",keys[s1]);}delete [] borrowTime;delete [] backTime;delete [] keys;delete [] keyID;return 0;
}?

CCF/CSP 201709-2 公共钥匙盒的求解 C++版相关推荐

  1. CCF 模拟题,公共钥匙盒

    题目描述: 有一个学校的老师共用N个教室,按照规定,所有的钥匙都必须放在公共钥匙盒里,老师不能带钥匙回家.每次老师上课前,都从公共钥匙盒里找到自己上课的教室的钥匙去开门,上完课后,再将钥匙放回到钥匙盒 ...

  2. CSP认证201709-2 公共钥匙盒[C++题解]:结构体、排序、枚举

    文章目录 题目解答 题目链接 题目解答 来源:acwing 分析: 采用结构体来存每个操作,保存啥呢?三个成员:钥匙id:操作的类型:1表示还钥匙,0表示取钥匙:操作的时间tm: 然后结构体内部排序, ...

  3. CCF CSP 201909-1小明种苹果 C语言版

    关键词:201909-1 小明种苹果 C语言 先上代码为敬,题目在后面 编译环境:Dev C++ 5.11 语言:C语言 #include <stdio.h> struct tree {i ...

  4. python认证考试_Python入门习题(39)——CCF CSP认证考试真题:公共钥匙盒

    CCF CSP认证考试真题:共钥匙盒 问题描述 试题编号:201709-2 试题名称:公共钥匙盒 时间限制:1.0s 内存限制:256.0MB 问题描述 有一个学校的老师共用N个教室,按照规定,所有的 ...

  5. CSP CCF 201709-2 公共钥匙盒(C++)满分代码,有注释

    问题描述 试题编号: 201709-2 试题名称: 公共钥匙盒 时间限制: 1.0s 内存限制: 256.0MB 问题描述: 问题描述 有一个学校的老师共用N个教室,按照规定,所有的钥匙都必须放在公共 ...

  6. CCF CSP 公共钥匙盒 JAVA 201709-2 100分

    这道题做了几遍 感觉这次做得比较好的就是做好了每个函数的封装 无非使用了二维数组的排序  就变成了很简单的一道题 package csp2017_09_2;import java.util.Array ...

  7. csp ccf公共钥匙盒

    问题描述 有一个学校的老师共用N个教室,按照规定,所有的钥匙都必须放在公共钥匙盒里,老师不能带钥匙回家.每次老师上课前,都从公共钥匙盒里找到自己上课的教室的钥匙去开门,上完课后,再将钥匙放回到钥匙盒中 ...

  8. CCF CSP 公共钥匙盒

    问题描述 试题编号: 201709-2 试题名称: 公共钥匙盒 时间限制: 1.0s 内存限制: 256.0MB 问题描述: 问题描述 有一个学校的老师共用N个教室,按照规定,所有的钥匙都必须放在公共 ...

  9. ccf公共钥匙盒python_CCF python 201709-2 公共钥匙盒

    基本思路: 将所有的时间节点(借钥匙时间,还钥匙时间)组织到一个列表里[钥匙号,时间,借or还] 并将之按时间的升序.还优先借.钥匙号的升序排列 那么所要做的就是遍历这个列表: ····如果是借就 · ...

最新文章

  1. (DT系列五)Linux kernel 是怎么将 devicetree中的内容生成plateform_device【转】
  2. 计算机网络---物理层
  3. bootsrap+jquery+组件项目引入文件的常见报错
  4. 采购退料单新增无法获取单价
  5. C语言逗号运算符和逗号表达式基础总结
  6. 最长回文子串——Manacher 算法​​​​​​​
  7. android 8.1.0怎么截屏,vivo Z1i怎么截屏?4种vivo Z1i截图方法
  8. 软工作业PSP与单元测试训练 15100231
  9. 第四周 项目中的白盒测试
  10. go 批量删除文件内字符串_leetcode1047_go_删除字符串中的所有相邻重复项
  11. 印前软件 数码打样 管理软件
  12. 职业生涯规划访谈记录关于计算机专业,计算机专业职业生涯规划书
  13. SQL SERVER “指定的网络名不再可用”
  14. Hadoop文件基础操作命令
  15. 想转行it , 培训还是自学?
  16. 字节跳动+京东+美团+腾讯面试总结,附赠课程+题库
  17. 如何查询一个域名的子域名
  18. 输出字符的ascii码
  19. html自动展示视频,html5纯css3带自动视频播放的iPhone4手机360度旋转展示
  20. 通用方法 关闭Outlook最小化非直接退出

热门文章

  1. 史考特 容易忽略的开户细节
  2. 【机器学习】李宏毅——Flow-based Generative Models
  3. TCP报文中的SYN,FIN,ACK,PSH,RST,UR
  4. 3836mysql数据库应用基础教程答案_mysql intersect
  5. 创新创业名词解释_“大众创业万众创新”相关名词解释总汇
  6. 用python爬取豆瓣某本书的前n条书评并计算评分(star)的平均值
  7. CalibNet:Geometrically Supervised Extrinsic Calibration using 3D Spatial Transformer Networks阅读理解
  8. RocketMQ的broker处理消息commit时,加锁应该使用自旋锁还是重入锁
  9. VSCrawler 爬虫 java.lang.NoClassDefFoundError: org/apache/commons/logging/LogFactory 解决方案
  10. 扬长避短,做自己最擅长的事情