【题目地址】
题意见原题面。
这个题如果学过闵可夫斯基和的话就非常好做。
直接将给出的两个点集,将其中一个坐标取反,然后先求出两个凸包,然后求这两个凸包的闵可夫斯基和,如果移动的向量组在这两个凸包的闵可夫斯基和中,那么就表示移动后会有交点,否则没有。
#include<cstdio>
#include<cstring>
#include<algorithm>
#define ll long long
using namespace std;
const int M=1e5+10;
int n,m,Q;
ll Sqr(ll x){return x*x;}
struct Point{
ll x,y;
void out(){printf("WA %lld %lld\n",x,y);}
ll len()const{return Sqr(x)+Sqr(y);}
Point(){}
Point(ll a,ll b):x(a),y(b){}
void rev(){x=-x;y=-y;}
void in(){scanf("%lld%lld",&x,&y);}
Point operator +(const Point &a)const{return Point(x+a.x,y+a.y);}
Point operator -(const Point &a)const{return Point(x-a.x,y-a.y);}
bool operator <(const Point &a)const{return x<a.x||(x==a.x&&y<a.y);}
}C1[M],C2[M],H1[M],H2[M],A[M],Ls;int tot,n1,m1;
ll dot(Point a,Point b){return a.x*b.x+a.y*b.y;}
ll cross(Point a,Point b){return a.x*b.y-a.y*b.x;}
int Convex(Point *p,Point *h,int nn){
sort(p+1,p+n+1);int Cnt=0;
for(int i=1;i<=nn;i++){
while(Cnt>1&&cross(h[Cnt]-h[Cnt-1],p[i]-h[Cnt-1])<=0)--Cnt;
h[++Cnt]=p[i];
} int k=Cnt;
for(int i=nn-1;i>=1;i--){
while(Cnt>k&&cross(h[Cnt]-h[Cnt-1],p[i]-h[Cnt-1])<=0)--Cnt;
h[++Cnt]=p[i];
} if(nn>1)--Cnt;
return Cnt;
}
void Minkovski(){
for(int i=1;i<n1;i++) C1[i]=H1[i+1]-H1[i];C1[n1]=H1[1]-H1[n1];
for(int i=1;i<m1;i++) C2[i]=H2[i+1]-H2[i];C2[m1]=H2[1]-H2[m1];
A[tot=1]=H1[1]+H2[1];
int p1=1,p2=1;
while(p1<=n1&&p2<=m1)
++tot,A[tot]=A[tot-1]+(cross(C1[p1],C2[p2])>=0?C1[p1++]:C2[p2++]);
while(p1<=n1) ++tot,A[tot]=A[tot-1]+C1[p1++];
while(p2<=m1) ++tot,A[tot]=A[tot-1]+C2[p2++];
}
bool cmp(const Point &a,const Point &b){return cross(a,b)>0||(cross(a,b)==0&&a.len()<b.len());}
bool isin(Point move){
if(cross(move,C1[1])>0||cross(C1[tot],move)>0) return 0;
int p=lower_bound(C1+1,C1+tot+1,move,cmp)-C1-1;
return cross((move-C1[p]),(C1[p%tot+1]-C1[p]))<=0;
}
int main(){
scanf("%d%d%d",&n,&m,&Q);
for(int i=1;i<=n;i++){
C1[i].in();
} n1=Convex(C1,H1,n);
for(int i=1;i<=m;i++){
C2[i].in();C2[i].rev();
} m1=Convex(C2,H2,m);
Minkovski();
tot=Convex(A,C1,tot);
Point st=C1[1];
for(int i=tot;i>=1;i--)C1[i]=C1[i]-C1[1];
while(Q--){
Ls.in();
printf("%d\n",isin(Ls-st));
}
return 0;
}