CF1032D Solution

题目链接

题解

可以分两类讨论\(A,B\)点间的最短路径,经过函数与不经过函数,其中不经过函数的情况曼哈顿距离即可。

可得在只能经过格点的情况下,点\(A\)到函数\(f\)最短距离的点\(x\)值与\(y\)值中一定有一项与\(A\)相等。
也就是如左图,点\(A\)到直线的最短距离一定为\(AD\)\(AC\)的最小值,\(B\)同理。

感谢机房神仙提供的证明!(。・∀・)ノ:

当斜率\(>1\)时右下(\(x\)相等时)同理。

因此经过函数的情况只需枚举上图中的\(C,D,E,F\),排列组合取最小值即可。

AC代码

#include<bits/stdc++.h>
using namespace std;
int main()
{
	double a,b,c,xa,xb,ya,yb;
	scanf("%lf%lf%lf%lf%lf%lf%lf",&a,&b,&c,&xa,&ya,&xb,&yb);
	double ans1=abs(xa-xb)+abs(ya-yb),ans2;
    //ans1:曼哈顿距离,ans2:经过函数的最短距离
	double tx1=-(b*ya+c)/a,ty1=-(a*xa+c)/b,tx2=-(b*yb+c)/a,ty2=-(a*xb+c)/b;
    //tx1:C的x值,ty1:D的y值,tx2:E的x值,ty2:F的y值
    //经过CF的情况
	ans2=abs(tx1-xa)+sqrt((tx1-xb)*(tx1-xb)+(ty2-ya)*(ty2-ya))+abs(ty2-yb);
    //经过DE的情况
	ans2=min(ans2,abs(tx2-xb)+sqrt((tx2-xa)*(tx2-xa)+(ty1-yb)*(ty1-yb))+abs(ty1-ya));
	//经过CE的情况
    ans2=min(ans2,abs(tx1-xa)+sqrt((tx1-tx2)*(tx1-tx2)+(ya-yb)*(ya-yb))+abs(tx2-xb));
	//经过DF的情况
    ans2=min(ans2,abs(ty1-ya)+sqrt((ty1-ty2)*(ty1-ty2)+(xa-xb)*(xa-xb))+abs(ty2-yb));
	printf("%lf",min(ans1,ans2));
	return 0;
}
posted @ 2021-01-09 10:26  violet_holmes  阅读(65)  评论(1编辑  收藏  举报