# [bzoj1027][JSOI2007]合金

n,m<=500

#include<iostream>
#include<cstring>
#include<cstdio>
#define INF 1000000000
#define MN 500
#define eps 1e-8
using namespace std;
{
int x = 0 , f = 1; char ch = getchar();
while(ch < '0' || ch > '9'){ if(ch == '-') f = -1;  ch = getchar();}
while(ch >= '0' && ch <= '9'){x = x * 10 + ch - '0';ch = getchar();}
return x * f;
}

int f[MN+5][MN+5];
int n,m;double Xmn=INF,Xmx=-INF,Ymn=INF,Ymx=-INF;
struct P{double x,y;
P(double x=0,double y=0):x(x),y(y){}
double operator^(P b){return x*b.y-y*b.x;}
P operator-(P b){return P(x-b.x,y-b.y);}
}p[MN+5],q[MN+5];

bool check(double x1,double x2,double x3,double x4)
{
if(x1>x2)swap(x1,x2);
return x1<=x3&&x4<=x2;
}

int solve(int x,int y)
{
int num1=0,num2=0;
for(int i=1;i<=m;i++)
{
double crs=(p[y]-p[x])^(q[i]-p[x]);
if(crs<-eps)num2++;
if(crs>eps) num1++;
}
if(!num1&&!num2&&check(p[x].x,p[y].x,Xmn,Xmx)&&check(p[x].y,p[y].y,Ymn,Ymx))return -1;
if(num1*num2)return 0;
if(num1)return 2;
if(num2)return 1;
return 3;
}

bool special()
{
for(int i=2;i<=n;i++)
if(p[i].x!=p[1].x||p[i].y!=p[1].y)return 0;
for(int i=1;i<=m;i++)
if(q[i].x!=p[1].x||q[i].y!=p[1].y)return 0;
return 1;
}

int main()
{
for(int i=1;i<=n;i++)
scanf("%lf%lf%lf",&p[i].x,&p[i].y,&d);
for(int i=1;i<=m;i++)
{
scanf("%lf%lf%lf",&q[i].x,&q[i].y,&d);
Xmn=min(Xmn,q[i].x);Xmx=max(Xmx,q[i].x);
Ymn=min(Ymn,q[i].y);Ymx=max(Ymx,q[i].y);
}
if(special())return 0*puts("1");
memset(f,63,sizeof(f));
for(int i=1;i<n;i++)
for(int j=i+1;j<=n;j++)
{
int res=solve(i,j);
if(res==-1)return 0*puts("2");
if(res&1)f[i][j]=1;
if(res&2)f[j][i]=1;
}
for(int k=1;k<=n;k++)
for(int i=1;i<=n;i++)
if(f[i][k]<=INF)
for(int j=1;j<=n;j++)
f[i][j]=min(f[i][j],f[i][k]+f[k][j]);
int minn=INF;
for(int i=1;i<=n;i++) minn=min(minn,f[i][i]);
if(minn>2&&minn<INF)printf("%d\n",minn);else puts("-1");
return 0;
}

posted @ 2017-04-03 21:39  FallDream  阅读(428)  评论(0编辑  收藏  举报