赛时磨了两个小时,模拟每一秒的变化就行了,模拟题要想清楚写这样思路比较清晰一些
#include<bits/stdc++.h>
using namespace std;
int n,m,h,k,q;//0-n-1 0-m-1 0-h-1
array<int,3> pos;
struct Elevter{
array<int,3> now;
int dir,idx;//dir 0 x 1:y 2:z
Elevter() =default;
Elevter(array<int,3> now,int dir,int idx):now(now),dir(dir),idx(idx){}
}elevter[8*8*10];
struct peo{
array<int,3> now; //位置
int lst_time,elev_idx; //上次乘坐时间,当前电梯编号没有-1
array<int,3> des; //目标位置
int emerge_time,now_dir; //出现时间,当前方向
peo()=default;
peo(array<int,3> now,int lst_time,int elev_idx,array<int,3> des,int emerge_time,int now_dir):
now(now),lst_time(lst_time),elev_idx(elev_idx),des(des),
emerge_time(emerge_time),now_dir(now_dir){}//elev_idx -1说明没有
}people[55];
bool check_in(peo &pe,Elevter elv,int time){//判断乘客是否可以乘坐电梯,同时操作(进电梯)
if(pe.elev_idx!=-1||pe.now==pe.des) return 0; //已经在电梯或者到终点
if(pe.now==elv.now&&pe.now_dir==elv.dir&&pe.lst_time<time
&&pe.emerge_time<=time){//位置一样并且出现时间小于当前时间
pe.elev_idx=elv.idx;//在乘客当前位置不用更新位置
return 1;
}else{
return 0;
}
}
bool check_out(peo &pe,Elevter elv,int time){//pe elevter[pe.elev_idx]
if(pe.elev_idx==-1||pe.now==pe.des) return 0; //没坐电梯或者到终点
if(pe.elev_idx==elv.idx&&elv.now[elv.dir]==pe.des[elv.dir]){ //电梯在该方向运行到目标位置,下电梯
//更新乘客位置和当前方向,上次下电梯时间
pe.now=elv.now;
while (pe.now_dir<3&&pe.now[pe.now_dir]==pe.des[pe.now_dir]) pe.now_dir++; //可能不止一个方向到达
pe.lst_time=time;
pe.elev_idx=-1;
return 1;
}else return 0;
}
//长宽高每个点从0开始可以直接取模
//一开始确定从那个方向走
signed main(){
ios::sync_with_stdio(0);cin.tie(0);
cin>>n>>m>>h;
cin>>k;
pos={n,m,h};
for(int i = 0;i<k;++i){
int type,ex,ey,ez;
cin>>type>>ex>>ey>>ez;//位置要-1
ex--;ey--;ez--;
//cout<<"ex ey ez: "<<ex<<" "<<ey<<" "<<ez<<"\n";
elevter[i] = Elevter({ex,ey,ez},type,i);
}
cin>>q;
for(int i = 0;i<q;++i){
int pt,fx,fy,fz,tx,ty,tz;
cin>>pt>>fx>>fy>>fz>>tx>>ty>>tz;
fx--;fy--;fz--;
tx--;ty--;tz--;
int dire=0; //是否有可能不用坐电梯?
if(fx==tx&&fy==ty) dire=2;
else if(fx==tx) dire=1;
else dire=0;
people[i]=peo({fx,fy,fz},0,-1,{tx,ty,tz},pt,dire);
}
vector<array<int,7>> log;
for(int time = 1;time<=800;++time){
//更新电梯情况
for(int i = 0;i<k;++i){
elevter[i].now[elevter[i].dir]+=1;
elevter[i].now[elevter[i].dir]%=pos[elevter[i].dir];
}
for(int i = 0;i<q;++i){ //人
for (int j =0;j<k;++j) {
if (check_out(people[i],elevter[j],time)) {
log.push_back({time,i,0,j,elevter[j].now[0],elevter[j].now[1],elevter[j].now[2]});
}
}
for(int j = 0;j<k;++j){ //电梯
if(check_in(people[i],elevter[j],time)){
//cout<<"sdasad\n";
log.push_back({time,i,1,j,people[i].now[0],people[i].now[1],people[i].now[2]});
}
}
}
}
sort(log.begin(),log.end(),[](array<int,7> x,array<int,7> y){
if(x[0]!=y[0]) return x[0]<y[0]; //time
else if(x[3]!=y[3]) return x[3]<y[3]; //电梯
else if(x[2]!=y[2]) return x[2]<y[2]; //进出
else if(x[1]!=y[1]) return x[1]<y[1];
else return x[4]<y[4];
});
for(auto &[time,ren,inout,elev,x,y,z]:log){
cout<<'['<<time<<"s] Person "<<ren+1<<" ";
if(inout) cout<<"IN ";
else cout<<"OUT ";
cout<<"Elevator "<<elev+1<<" at (";
cout<<x+1<<", ";
cout<<y+1<<", ";
cout<<z+1<<")\n";
}
return 0;
}