【题目描述】
小 C 每到午饭时间,总是第一个冲向食堂。
食堂有一排 n 个窗口,第 i 号窗口有一个坐标 xi,不一定满足坐标递增。
小 C 爱食堂,小朋友们也爱食堂。
食堂里总共有 m 位小朋友,第 i 位小朋友的坐标为 yi,不一定满足坐标递增 。由于避免拥挤,所以有 m ≤ n,即每位小朋友至少能找到一个窗口自己独享。
总而言之,可以将食堂看成一个数轴,窗口和小朋友看成若干个坐标点。
在小朋友的世界中,他们遵循着一套规则:从 0 时刻开始,每过 1 秒钟,每位小朋友朝向最近的、还没小朋友停留的窗口移动 1 的距离,如果到两个窗口的距离相等,选择编号最小的窗口;当一个窗口有小朋友的时候,在该处编号最小的小朋友将在此窗口停留;当小朋友停留后,就不会再移动了。
现在小 C 掌握了这套规则,他想知道每位小朋友停留的时刻以及停留的窗口,这样小 C 就能赶在小朋友到达某个窗口前抢到饭。
保证窗口两两坐标不同,不保证小朋友两两坐标不同,不保证初始时小朋友与窗口坐标不同。
【输入】
共三行,第一行两个正整数 n 和 m,表示窗口数和小朋友个数;
第二行共 n 个整数,第 i 个数为 xi,描述了窗口的坐标;
第三行共 m 个整数,第 i 个数为 yi,描述了小朋友的坐标。
窗口和小朋友的坐标不一定满足递增。
【输出】
共 m 行,每行两个整数,第 i 行的描述编号为 i 的小朋友,依次表示小朋友停留的时刻、停留的窗口的编号。
【1#输入样例】
4 3 3 -3 9 -11 2 2 0
【1#输出样例】
1 1 15 3 5 2
【2#输入样例】
6 6
2 -1 0 3 5 -6
1 1 -1 -1 3 4
【2#输出样例】
1 1
9 6
0 2
1 3
0 4
1 5
【数据规模及约定
#include<stdio.h>
int n,m;
bool ck[1001],hz[1001];//ck为窗口是否被占领,hz为小朋友是否放置
int kid[1001],win[1001];//kid为孩子坐标,win为窗口坐标
int t[1001][2];//0为时间,1为小朋友序号,t[i][ ]为第i个kid
int k;//停时间
int abs(int x)
{
if(x>=0)
return x;
return -x;
}
int min(int a,int b)
{
if(a<b)
return a;
return b;
}
int main()
{
scanf("%d%d",&n,&m);
for(int i=1;i<=n;i++)
scanf("%d",&win[i]);
for(int i=1;i<=m;i++)
scanf("%d",&kid[i]);
int people=m;
while(1)
{
for(int i=1;i<=n;i++)
{
for(int j=1;j<=m;j++)
{
if(ck[i]==true)
break;
if(kid[j]==win[i]&&hz[j]==false)
{
people--;
ck[i]=true;
hz[j]=true;
t[j][0]=k;
t[j][1]=i;
break;
}
}
}
if(people==0)
{
for(int i=1;i<=m;i++)
printf("%d %d\n",t[i][0],t[i][1]);
return 0;
}
int mn;
int mnmm=2100000000;
int windowx[1001];
for(int i=1;i<=m;i++)
{
if(hz[i]==true)
continue;
mn=1685943201;
for(int j=1;j<=n;j++)
{
if(ck[j]==true)
continue;
if(abs(win[j]-kid[i])<mn)
mn=abs(win[j]-kid[i]),windowx[i]=win[j];
mnmm=min(mnmm,mn);
}
}
for(int i=1;i<=m;i++)
{
if(hz[i]==true)
continue;
if(kid[i]-windowx[i]>0)
kid[i]-=mnmm;
else
kid[i]+=mnmm;
}
k+=mnmm;
}
return 0;
}