题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=1050
题目大意:从房间i移到到房间j,在移动过程中,走廊i-j这一个部分被占用。只要不共用走廊的移动都可同时进行,每移动一次需要10分钟。
题目分析:
1.注意房间构造,奇数房间在上面,偶数房间在下面,但是相对的房间占用同一个走廊。所以我们把房间都转换为同一边。
room=(room+1)/2; //房间号处理,变为1-200
2.输入要求说明,每个房间只会出现一次;
3.输入情况可能出现房间号大小顺序问题,所以为方便,我们进行处理,将小的房间号放前面;
4.区间贪心要多次进行,因为每次我们只是把一种情况可同时搬运的计算出来,可能还有另外几种情况;
思路一:区间贪心
struct Room{
int s,t;
bool flag;
}r[205];
bool cmp(Room r1,Room r2){
return r1.t<r2.t; //必须采用开始房间号小排序,使用结束房间号排序会出错
}
void swap(int &a,int &b){
int temp=a;
a=b;
b=temp;
}
int main(){
int N;
cin>>N;
while(N--){
int count=0;
int n;
cin>>n;
for(int i=0;i<n;i++){
cin>>r[i].s>>r[i].t;
r[i].flag=true;
if(r[i].s>r[i].t) //房间号大小顺序处理
swap(r[i].s,r[i].t);
//房间号处理
r[i].s=(r[i].s+1)/2;
r[i].t=(r[i].t+1)/2;
}
sort(r,r+n,cmp); //排序
int jl;
int k=0;
while(k<n){ //要循环进行
jl=0;
for(int i=0;i<n;i++){
if(r[i].flag&&r[i].s>jl){
k++;
jl=r[i].t;
r[i].flag=false;
}
}
count++;
}
cout<<count*10<<endl;
}
return 0;
}
要按开始房间号从小到大排序,而不是结束房间号。
1 4 2 10 4 6 8 16 12 14
思路二,对走廊进行分析,计算走廊被重复利用次数。
void swap(int &a,int &b){
int temp=a;
a=b;
b=temp;
}
int main(){
int N;
cin>>N;
while(N--){
int corridor[205]={0,};
int n;
cin>>n;
for(int i=0;i<n;i++){
int a,b;
cin>>a>>b;
if(a>b)
swap(a,b);
a=(a+1)/2;
b=(b+1)/2;
for(int j=a;j<=b;j++){
corridor[j]++;
}
}
sort(corridor+1,corridor+201); //从小到大排序,最后一个是走廊被重复利用的最多次数
cout<<corridor[200]*10<<endl;
}
return 0;
}