三点构成三个点对的路径,x轴、y轴都至少有一个点对的路径经过。
枚举每组点对的路径让其经过一个轴,当然也可以同时经过两个轴。在所有情况中取最小答案。
当坐标在轴同一侧时,对其中一个点的该坐标取反,得到的新点求距离就是镜面反射的距离。
如果在不同侧,就直接求距离。
1 #include<stdio.h> 2 #include<stdlib.h> 3 #include<math.h> 4 #include<algorithm> 5 const double eps = 1e-8; 6 inline double Sqr(double x) {return x * x;} 7 struct Point 8 { 9 double x, y; 10 double Dis(const Point &b)const{return sqrt(Sqr(x - b.x) + Sqr(y - b.y));} 11 }; 12 Point p[4], lin; 13 double CalDis(int i, bool nx, bool ny) 14 { 15 Point lin = p[i]; 16 if(nx && p[i].x * p[i + 1].x > -eps) lin.x = -lin.x; 17 if(ny && p[i].y * p[i + 1].y > -eps) lin.y = -lin.y; 18 return lin.Dis(p[i + 1]); 19 } 20 int main() 21 { 22 int t, i, j; 23 double dis, ans; 24 for(scanf("%d", &t); t --; ) 25 { 26 for(i = 0; i < 3; i ++) scanf("%lf%lf", &p[i].x, &p[i].y); 27 p[3] = p[0], ans = 1e30; 28 for(i = 0; i < 3; i ++) for(j = 0; j < 3; j ++) 29 { 30 dis = 0; 31 if(i == j) dis = CalDis(i, true, true) + p[i + 1].Dis(p[(i + 2) % 3]) + p[i].Dis(p[(i + 2) % 3]); 32 else dis = CalDis(i, true, false) + CalDis(j, false, true) + p[3 - i - j].Dis(p[4 - i - j]); 33 ans = std::min(ans, dis); 34 } 35 printf("%.2f\n", ans); 36 } 37 return 0; 38 }