UVALive - 4043 Ants (KM裸题)

来源:互联网 发布:金盏花洁面啫喱知乎 编辑:程序博客网 时间:2024/05/18 23:13

题目大意:给出N只蚂蚁和N棵树的坐标,问如何完美匹配,才能使蚂蚁到树的连线不会相交

解题思路:KM裸题,但是很郁闷啊
不开根号,用long long竟然过不了,很无语啊,距离最大只有8亿啊
然后用A的double的代码,把他改成了long long ,WA了
然后再用double的A的代码,不开根了,又WA了,这题真坑到底是什么鬼

#include <cstdio>#include <cstring>#include <algorithm>#include <cmath>using namespace std;#define N 110#define INF 1e20#define esp 1e-10struct Node{    double x, y;}Ants[N], Apple[N];double w[N][N];double lx[N], ly[N];int left[N], n;bool S[N], T[N];void init() {    for (int i = 1; i <= n; i++)        scanf("%lf%lf", &Ants[i].x, &Ants[i].y);    for (int i = 1; i <= n; i++)        scanf("%lf%lf", &Apple[i].x, &Apple[i].y);    double x1, x2, y1, y2;    for (int i = 1; i <= n; i++) {        x1 = Apple[i].x;         y1 = Apple[i].y;        for (int j = 1; j <= n; j++) {            x2 = Ants[j].x;            y2 = Ants[j].y;            w[i][j] = -sqrt((x1 - x2) * (x1 - x2) + (y1 - y2) * (y1 - y2));        }    }}bool match(int u) {    S[u] = true;    for (int j = 1; j <= n; j++) {        if (fabs(lx[u] + ly[j] - w[u][j]) < esp && !T[j]) {            T[j] = true;            if (!left[j] || match(left[j])) {                left[j] = u;                return true;            }        }    }    return false;}void update() {    double Min = INF;    for (int i = 1; i <= n; i++) if (S[i])         for (int j = 1; j <= n; j++) if (!T[j])             Min = min(lx[i] + ly[j] - w[i][j], Min);    for (int i = 1; i <= n; i++) {        if (S[i]) lx[i] -= Min;        if (T[i]) ly[i] += Min;    }}void EK() {    for (int i = 1; i <= n; i++) {        left[i] = ly[i] = 0;        lx[i] = -INF;        for (int j = 1; j <= n; j++)            lx[i] = max(lx[i], w[i][j]);    }    for (int i = 1; i <= n; i++) {        while(1) {            for (int j = 1; j <= n; j++)  S[j] = T[j] = 0;            if (match(i)) break; else update();        }    }}int main() {    int cnt = 0;    while (scanf("%d", &n) != EOF) {        if (cnt++)            printf("\n");        init();        EK();        for (int i = 1; i <= n; i++)            printf("%d\n", left[i]);    }    return 0;}
0 0
原创粉丝点击