hdu 4305 生成樹計數
阿新 • • 發佈:2019-02-17
此題建圖稍顯麻煩,我先固定一個點,然後對斜率排序,斜率則寫成了分數形式,然後嘛就是上模板
#include <utility> #include <algorithm> #include <string> #include <cstring> #include <cstdio> #include <iostream> #include <iomanip> #include <set> #include <vector> #include <cmath> #include <queue> #include <bitset> #include <map> using namespace std; #define clr(a,v) memset(a,v,sizeof(a)) #define lson l,m,rt<<1 #define rson m+1,r,rt<<1|1 const int INF = 0x7f7f7f7f; const int maxn = 311; const int mod = 10007; const double pi = acos(-1.0); const double eps = 1e-10; typedef long long ll; typedef pair<int, int> pii; typedef vector<int> VI; typedef vector<VI> VVI; typedef vector<VVI> VVVI; typedef pair<int, int> pii; struct node { int x, y, dis, id; node() { } node(int x, int y, int dis, int id) : x(x), y(y), dis(dis), id(id) { } } p[maxn << 2]; inline bool same(long x, long y) { return (x >> 31) == (y >> 31); } inline int cross(const node& a, const node& b) { return a.x * b.y - a.y * b.x; } bool cmp(const node& a, const node& b) { int t = cross(a, b); if (!t) return a.dis < b.dis; return same(t, a.y * b.y); } int f[maxn], n, m; int r[maxn], x[maxn], y[maxn]; int det[maxn][maxn]; int Det(int n) { int ans = 1; int i, j, k, t; for (i = 0; i < n; ++i) { for (j = i + 1; j < n; ++j) { while (det[j][i]) { t = det[i][i] / det[j][i]; for (k = i; k < n; ++k) { det[i][k] -= det[j][k] * t; det[i][k] %= mod; swap(det[i][k], det[j][k]); } ans *= -1; } } if (!det[i][i]) return 0; } for (i = 0; i < n; ++i) ans = ans * det[i][i] % mod; ans = (ans % mod + mod) % mod; return ans; } int find(int n) { return f[n] == n ? n : f[n] = find(f[n]); } void Union(int x, int y) { int a = find(x); int b = find(y); if (a != b) f[a] = b, r[b] += r[a]; } int main() { int R, i, j, cnt, T, dis, dx, dy; scanf("%d", &T); while (T--) { clr(det,0); scanf("%d%d", &n, &R); R *= R; for (i = 0; i < n; ++i) f[i] = i, r[i] = 1; cnt = 0; for (i = 0; i < n; ++i) scanf("%d%d", x + i, y + i); for (i = 0; i < n; ++i) { cnt = 0; for (j = i + 1; j < n; ++j) { dx = x[i] - x[j]; dy = y[i] - y[j]; dis = dx * dx + dy * dy; if (dis <= R) p[cnt++] = node(dx, dy, dis, j); } sort(p, p + cnt, cmp); for (j = 0; j < cnt; ++j) { if (!j || cross(p[j], p[j - 1])) { det[i][i]++; det[p[j].id][p[j].id]++; det[i][p[j].id] = -1; det[p[j].id][i] = -1; Union(i, p[j].id); } } } int u = find(0); if (r[u] < n) puts("-1"); else printf("%d\n", Det(n - 1)); } return 0; }