HDOJ 5839 计算几何+暴力
链接:
http://acm.hdu.edu.cn/showproblem.php?pid=5839
题意:
给你立体空间内的n个点,问能组成多少个四面体满足
1.至少四条棱相等
2.如果刚好四条棱相等,那么不相等的两条棱不能相邻
题解:
直接暴力,先枚举3个点,如果这三个点组成的三角形三边都不相等,那么就不用枚举第四个点了,其实很多情况都不用枚举第四个点
如果这个三角形是等边或等腰三角形,再分别枚举第四个点,分情况计算
开始的时候忘了判断还要判断四点共面,所以没用Point结构体,结果连样例都过不了,所以代码写的非常乱。。
代码:
31 int n; 32 double x[222], y[222], z[222]; 33 double dis[222][222]; 34 35 double sqr(double x) { 36 return x*x; 37 } 38 39 double dist(int a, int b) { 40 return sqrt(sqr(x[a] - x[b]) + sqr(y[a] - y[b]) + sqr(z[a] - z[b])); 41 } 42 43 struct Point { 44 double x, y, z; 45 Point(double x, double y, double z) :x(x), y(y), z(z) {} 46 }; 47 48 Point operator -(const Point &a, const Point &b) { 49 return Point(a.x - b.x, a.y - b.y, a.z - b.z); 50 } 51 52 Point det(Point a, Point b) { 53 return Point(a.y*b.z - a.z*b.y, a.z*b.x - a.x*b.z, a.x*b.y - a.y*b.x); 54 } 55 56 double dot(Point a, Point b) { 57 return a.x*b.x + a.y*b.y + a.z*b.z; 58 } 59 60 Point pvec(Point s1, Point s2, Point s3) { 61 return det((s1 - s2), (s2 - s3)); 62 } 63 64 bool zero(double x) { 65 return fabs(x) < 1e-8; 66 } 67 68 bool check(int a, int b, int c, int d) { 69 Point A(x[a], y[a], z[a]); 70 Point B(x[b], y[b], z[b]); 71 Point C(x[c], y[c], z[c]); 72 Point D(x[d], y[d], z[d]); 73 return zero(dot(pvec(A, B, C), D - A)); 74 } 75 76 int main() { 77 ios::sync_with_stdio(false), cin.tie(0); 78 int T; 79 cin >> T; 80 rep(cas, 0, T) { 81 cin >> n; 82 rep(i, 0, n) cin >> x[i] >> y[i] >> z[i]; 83 rep(i, 0, n) rep(j, 0, n) dis[i][j] = dist(i, j); 84 int ans = 0; 85 rep(i, 0, n - 3) rep(j, i + 1, n - 2) rep(k, j + 1, n - 1) { 86 double a = dis[i][j]; 87 double b = dis[j][k]; 88 double c = dis[k][i]; 89 if (a != b && b != c && c != a) continue; 90 if (a == b && b == c) rep(h, k + 1, n) { 91 if (check(i, j, k, h)) continue; 92 double d = dis[h][i]; 93 double e = dis[h][j]; 94 double f = dis[h][k]; 95 int sum = 0; 96 if (d != a) sum++; 97 if (e != a) sum++; 98 if (f != a) sum++; 99 if (sum <= 1) ans++; 100 } 101 else rep(h, k + 1, n) { 102 if (check(i, j, k, h)) continue; 103 double d = dis[h][i]; 104 double e = dis[h][j]; 105 double f = dis[h][k]; 106 int fg = 0; 107 if (a == b) { 108 if (d == a && f == a) fg = 1; 109 } 110 else if (b == c) { 111 if (d == b && e == b) fg = 1; 112 } 113 else if (c == a) { 114 if (e == c && f == c) fg = 1; 115 } 116 if (fg) ans++; 117 } 118 } 119 cout << "Case #" << cas + 1 << ": "; 120 cout << ans << endl; 121 } 122 return 0; 123 }