QOJ.ac

QOJ

IDProblemSubmitterResultTimeMemoryLanguageFile sizeSubmit timeJudge time
#476419#8082. Minimum Euclidean DistanceError_666WA 0ms3888kbC++202.5kb2024-07-13 19:25:382024-07-13 19:25:38

Judging History

你现在查看的是最新测评结果

  • [2024-07-13 19:25:38]
  • 评测
  • 测评结果:WA
  • 用时:0ms
  • 内存:3888kb
  • [2024-07-13 19:25:38]
  • 提交

answer

#include <bits/stdc++.h>
using namespace std;

const int N = 5000 + 10;

struct A {
	double v;
	double p;
} a[N];
int n, q;
vector<double> dot_x, dot_y;

double getD(double a, double b, double c, double x, double y) {
	
    return fabs(a * x + b * y + c) / sqrt(a * a + b * b);
}

double get(double x1, double y1, double x2, double y2) {
	double d1 = (x1 - x2) * (x1 - x2);
	double d2 = (y1 - y2) * (y1 - y2);
	return sqrt(d1 + d2);
}

bool cmp(A x, A y) {
	return x.v < y.v;
}

int main()
{
	scanf("%d%d", &n, &q);
	for (int i = 1; i <= n; i++) {
		double t1, t2;
		scanf("%lf%lf", &t1, &t2);
		dot_x.push_back(t1);
		dot_y.push_back(t2);
	}
	dot_x.push_back(dot_x[0]);
	dot_y.push_back(dot_y[0]);
	
	for (int i = 1; i <= q; i++) {
		double x, y, z, w, r;
		scanf("%lf%lf%lf%lf", &x, &y, &z, &w);
		// 圆心坐标是x, y
		r = get(x, y, z, w) / 2;
		x = (x + z) / 2;
		y = (y + w) / 2;
		
		// 判断圆心是否一开始就在凸包内
		int flag = 0, f1 = 0, f2 = 0;
		for (int j = 0; j < n; j++) {
			double x1 = dot_x[j], y1 = dot_y[j];
			double x2 = dot_x[j + 1], y2 = dot_y[j + 1];
			
			double vx1 = x2 - x1, vy1 = y2 - y1;
			double vx2 = x - x1, vy2 = y - y1;
			
			if (vx1 * vy2 - vx2 * vy1 > 0) {
				if (f2) {
					flag = 1;
					break;
				}
				f1 = 1;
			}
			else if (vx1 * vy2 - vx2 * vy1 < 0) {
				if (f1) {
					flag = 1;
					break;
				}
				f2 = 1;
			}
		}
		if (!flag) {
			double ans = (r * r / 2);
			printf("%.10lf\n", ans);
			continue;
		}
		
		for (int j = 0; j < n; j++) {
			double x1 = dot_x[j], y1 = dot_y[j];
			a[j + 1].v = get(x, y, x1, y1);
			a[j + 1].p = j;
		}
		sort(a + 1, a + 1 + n, cmp);
		
		// 找到了对应的直线
		double x1 = dot_x[a[1].p], y1 = dot_y[a[1].p];
		double x2 = dot_x[a[2].p], y2 = dot_y[a[2].p];
		if (x1 > x2) swap(x1, x2);
		if (y1 > y2) swap(y1, y2);
		
		// 要判断斜率是否存在
		double X, Y;
		if (x1 == x2) {
			X = x1;
			Y = y;
		}
		else {
			double A = (y2 - y1) / (x2 - x1);
			double B = -1;
			double C = (x2 * y1 - x1 * y2) / (x2 - x1);
			X = (A * B) / (A * A + B * B) * (B / A * x - C / B - y);
			Y = (-A * X - C) / B;
		}
		
		// 判断是否在中间
		if (x1 <= X && X <= x2 && y1 <= Y && Y <= y2) ;
		else {
			double d1 = get(x, y, x1, y1);
			double d2 = get(x, y, x2, y2);
			if (d1 < d2) X = x1, Y = y1;
			else X = x2, Y = y2;
		}
		
		double ans = (r * r / 2) + (X - x) * (X - x) + (Y - y) * (Y - y);
		printf("%.10lf\n", ans);
	}
	return 0;
}

Details

Tip: Click on the bar to expand more detailed information

Test #1:

score: 100
Accepted
time: 0ms
memory: 3888kb

input:

4 3
0 0
1 0
1 1
0 1
0 0 1 1
1 1 2 2
1 1 2 3

output:

0.2500000000
0.7500000000
1.8750000000

result:

ok Your answer is acceptable!^ ^

Test #2:

score: -100
Wrong Answer
time: 0ms
memory: 3888kb

input:

48 10
-30 0
-29 -4
-28 -7
-27 -9
-25 -12
-22 -16
-21 -17
-17 -20
-14 -22
-12 -23
-9 -24
-5 -25
-4 -25
0 -24
3 -23
5 -22
8 -20
12 -17
13 -16
16 -12
18 -9
19 -7
20 -4
21 0
21 1
20 5
19 8
18 10
16 13
13 17
12 18
8 21
5 23
3 24
0 25
-4 26
-5 26
-9 25
-12 24
-14 23
-17 21
-21 18
-22 17
-25 13
-27 10
-28 ...

output:

589.5000000000
51.4705882353
1051.2500000000
66.6250000000
134.3750000000
528.8750000000
272.3942307692
263.8750000000
689.6250000000
436.2500000000

result:

wrong answer Except 174.125000000000, but found 134.375000000000!QAQ