转自:http://www.cnblogs.com/wuyiqi/archive/2012/05/01/2477735.html
题目链接:http://codeforces.com/problemset/problem/46/D
题目大意:
在长为L的(点0~点L)的线段上停车开车操作;
停车 1 x:车长x,需要b+x+f的空余才能使车停进去,多个区域,选择最左边
开车 2 x:第x次操作,停进的车,开出去
分析:因为需要插入的次数很小,所以可以直接记录,每辆汽车一次插入的位置,被占据的位置和空位间肯定是一段一段相邻的
即,比如有空位 a-b、c-d, b-c 被占据了,如果a-b不够长,那么指针就要往右移动两个位置了,即跳过中间被占据的位置
#include <cstdio>
#include <cstring>
#include <vector>
#include <set>
#include <algorithm>
using namespace std;
int L, B, F;
int pos[105][2], tm=0;
set<int> s;
int main(void) {
scanf("%d%d%d", &L, &B, &F);
s.insert(-B);
s.insert(L+F);
int n;
scanf("%d", &n);
while(n--) {
int x, y;
scanf("%d%d", &x, &y);
++tm;
if (x == 1) {
int f=0;
for(set<int>::iterator it=s.begin(); it!=s.end(); ) {
set<int>::iterator nxt=it;
++nxt;
if (nxt!=s.end() && ((*it)+B+y+F <= *nxt)) {
printf("%d\n", (*it)+B);
s.insert((*it)+B);
s.insert((*it)+B+y);
pos[tm][0] = *it+B;
pos[tm][1] = *it+B+y;
f=1;
break;
}
++it; if(it!=s.end()) ++it;
}
if(!f) puts("-1");
} else {
s.erase(pos[y][0]);
s.erase(pos[y][1]);
}
}
return 0;
}