来源:http://codeforces.com/gym/101375/problem/C
题解:A就把盘子放到桌面上,R就把盘子从桌面上拿走,A输出No的可能性有3种:1.盘子之前放过了,vis数组标记,1为在桌上了,0为不在。2.盘子的坐标x<0||y<0||x>1000||y>1000,即在桌子外面,3.该盘子与其他盘子重叠了,即这句话
(an[j].r+an[i].r)*(an[j].r+an[i].r)>(an[j].x-an[i].x)*(an[j].x-an[i].x)+(an[j].y-an[i].y)*(an[j].y-an[i].y)
R输出No的可能性有2种:1.盘子不在桌上,即该坐标的vis为0 。 2.该盘子在桌子上,但是半径不符合真实大小。用rr来记录放在这一点坐标的盘子的半径
用结构体存每个点,注意特殊情况的判断即可ac
代码实现:
#include <iostream>
#include <cstring>
#include <algorithm>
#define N 5005
using namespace std;
int vis[1005][1005];
int rr[1005][1005];
struct
{
char c;
int x;
int y;
int r;
}an[N];
int main()
{
memset(vis,0,sizeof(vis));
memset(rr,0,sizeof(rr));
int t,j;
cin>>t;
for(int i=1;i<=t;++i)
{
cin>>an[i].c>>an[i].x>>an[i].y>>an[i].r;
if(an[i].x<0||an[i].y<0||an[i].x>1000||an[i].y>1000)
{
cout<<"No"<<endl;
continue;
}
if(an[i].c=='R')
{
if(vis[an[i].x][an[i].y]!=0&&rr[an[i].x][an[i].y]==an[i].r)
{
cout<<"Ok"<<endl;
vis[an[i].x][an[i].y]=0;
}
else
cout<<"No"<<endl;
}
else if(an[i].c=='A')
{
if(vis[an[i].x][an[i].y]!=0)
cout<<"No"<<endl;
else
{
for(j=1;j<=i-1;++j)
{
if(an[j].c=='A'&&vis[an[j].x][an[j].y]!=0&&rr[an[j].x][an[j].y]==an[j].r)
{
if((an[j].r+an[i].r)*(an[j].r+an[i].r)>(an[j].x-an[i].x)*(an[j].x-an[i].x)+(an[j].y-an[i].y)*(an[j].y-an[i].y))
{
cout<<"No"<<endl;
break;
}
}
}
if(j==i)
{
cout<<"Ok"<<endl;
vis[an[i].x][an[i].y]=1;
rr[an[i].x][an[i].y]=an[i].r;
}
}
}
}
return 0;
}