标签:des style blog http color io os ar for
Description
Input
Output
Sample Input
3 2 1 3 3 4 2 0
Sample Output
2 1 3 2 4 2
大致题意:很久以前,少林寺里只有一个等级10^9为方丈,他编号为1,少林寺里有个规矩,每个新来的和尚都必须和一位等级最接近自己的老(就是比他先来的)和尚进行战斗,后来又来了n个和尚,并且他们按入寺时间依次编号2~n+1,但是时间太久,方丈已经不知道每个和尚来的时候是跟哪个和尚战斗了,但是他还是记得哪个和尚比哪个和尚先来的。输入给出n个和尚的编号和他们的等级。下面就靠你了,让你依次求出每个和尚进寺是是跟谁战斗的,并输出。
解题思路:直接开数组的话,每次找跟他等级最接近的肯定要排序,目前知道的最快的快排的也是O(n*lg n)的,由于数据给的是10^5,再加上还要操作,时间已经超了。所以,得换个思路,那就得用到STL中的map的优势了,也好久没用map做题了。map里的数据会自动按键值升序排列,据说map内部的排序是用红黑树(一种不明觉厉的数据结构)实现的,其时间复杂度是O(n)的,同时,map里还可以直接用find()按键值查找键值所在的迭代器,这就太方便了。
具体实现步骤:1.先开个map<int, int> monk, 把方丈的编号id和等级grad在map里建立映射,这里用到了一个小细节,
建立映射可以直接这样写,monk[grad] = id.
2.在循环输入n个和尚的信息,
1)每次输入一个和尚的信息,然后在map里建立映射;
2)此时用find(grad)寻找当前加入的和尚所在的迭代器;
3)然后,考虑当前的迭代器的位置,若是最后一个,就直接输出当前迭代器的前一个;
要是第一个,就输出当前迭代器的后面一个;
要既不是第一个也不是最后一个的话,就比较当前迭代器的first和它前后两迭代器first之间的差值哪个更小,小的输出;
要是两差值一样的话,输出前一个迭代器。
AC代码:
#include <stdio.h> #include <string.h> #include <iostream> #include <algorithm> #include <vector> #include <queue> #include <set> #include <map> #include <string> #include <math.h> #include <stdlib.h> #include <time.h> using namespace std; #define INF 0x7fffffff map<int, int> a; //声明一个map对象 int main() { #ifdef sxk freopen("in.txt","r",stdin); #endif int n, k, g; while(scanf("%d",&n)!=EOF && n) { a[1e9] = 1; //处理方丈 for(int i=0; i<n; i++){ scanf("%d%d", &k, &g); a[g] = k; map<int, int>::iterator temp = a.find(g); //按grad查找当前和尚所在的迭代器 if(temp == a.begin()) printf("%d %d\n", k, (++temp)->second); else if(temp == a.end()) printf("%d %d\n", k, (--temp)->second); else{ if(abs((--temp)->first - (++temp)->first) > abs((++temp)->first - (--temp)->first)) printf("%d %d\n", k, (++temp)->second); else printf("%d %d\n", k, (--temp)->second); } } a.clear(); } return 0; }
标签:des style blog http color io os ar for
原文地址:http://blog.csdn.net/u013446688/article/details/39761223