题意:给你原图的大小H*W,然后给出缩小图的四个角的坐标,左下,右下,右上,左上,求哪个点与原来的点的位置是重合的。
题解:模拟退火,向四个角靠近,找dist==0的地方。
AC代码:
#include<stdio.h>
#include<math.h>
#define eps 1e-13
struct Point
{
double x,y;
Point(){}
Point(double x,double y)
{
this->x=x;
this->y=y;
}
}p[4],dir[4];
Point operator-(Point a,Point b)
{
return Point(a.x-b.x,a.y-b.y);
}
Point operator+(Point a,Point b)
{
return Point(a.x+b.x,a.y+b.y);
}
Point operator*(Point a,double k)
{
return Point(a.x*k,a.y*k);
}
double W,H;
double dist(Point a,Point b)
{
return sqrt((a.x-b.x)*(a.x-b.x)+(a.y-b.y)*(a.y-b.y));
}
bool Search()
{
Point start=Point(0,0);
double T=1.0,t;
double ans=dist(p[0],start);
for(int k=1;k<=10000;k++)
{
bool flag=1;
int g=0;
while(flag)//提高精度
{
flag=0;
for(int i=0;i<4;i++)
{
Point now=start*(1.0-T)+dir[i]*T;//向四个点靠近
Point nxt=(p[1]-p[0])*(now.x/W)+(p[3]-p[0])*(now.y/H)+p[0];
if(dist(nxt,now)+eps<ans)
{
ans=dist(nxt,now);
start=now;
flag=1;
}
}
}
T*=0.98;
}
if((fabs(ans)<1e-4))
{
printf("%.6f %.6f\n",start.x,start.y);
return 1;
}
return 0;
}
int main()
{
scanf("%lf%lf",&H,&W);
for(int i=0;i<4;i++)
scanf("%lf%lf",&p[i].x,&p[i].y);
dir[0]=Point(0,H);
dir[1]=Point(W,0);
dir[2]=Point(0,0);
dir[3]=Point(W,H);
Search();
}