hdu4463Prim简单变形

最小生成树Prim算法的简单变形,Prim算法就是贪心的思想,从任一点开始,依次选择离已知点最近的点扩展,那么这题只要初始的时候把给出的两点加到已知点中即可。

/*
 * hdu4463/win.cpp
 * Created on: 2012-11-17
 * Author    : ben
 */
#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <cmath>
#include <ctime>
#include <iostream>
#include <algorithm>
#include <queue>
#include <set>
#include <map>
#include <stack>
#include <string>
#include <vector>
#include <deque>
#include <list>
#include <functional>
#include <numeric>
#include <cctype>
using namespace std;
/**
 * 普里姆算法求最小生成树。map存储图的邻接矩阵。
 * N为图的顶点数
 * 返回最小生成树的权值,返回-1表示图不连通
 * typec可以是int、float、double等类型
 */
typedef double typec;
const int MAXN = 60;
const typec INF = 0x7fffffff;
typec graph[MAXN][MAXN];
int N, p, q;
typec MST_Prim() {
    typec lowcost[MAXN];
    int i, j, k;
    typec minc, ret = 0;
    copy(graph[p], graph[p] + N, lowcost);
    lowcost[q] = lowcost[p] = -INF;
    ret += graph[p][q];
    for(int j = 0; j < N; j++) {
        if(lowcost[j] > graph[q][j]) {
            lowcost[j] = graph[q][j];
        }
    }
    for(i = 2; i < N; i++) {
        minc = INF;
        for(j = 0; j < N; j++) {
            if(lowcost[j] > -INF && lowcost[j] < minc) {
                minc = lowcost[j];
                k = j;
            }
        }
        if(minc == INF) {
            return -1;
        }
        ret += minc;
        lowcost[k] = -INF;
        for(j = 0; j < N; j++) {
            if(lowcost[j] > graph[k][j]) {
                lowcost[j] = graph[k][j];
            }
        }
    }
    return ret;
}

typedef pair<int, int> MyPoint;

inline double mydis(const MyPoint &p1, const MyPoint &p2) {
    return sqrt((p1.first - p2.first) * (p1.first - p2.first) + (p1.second - p2.second) * (p1.second - p2.second));
}

void build_graph() {
    int a, b;
    scanf("%d%d", &p, &q);
    p--, q--;
    vector<pair<int, int> > g;
    for(int i = 0; i < N; i++) {
        scanf("%d%d", &a, &b);
        g.push_back(make_pair(a, b));
    }
    for(int i = 0; i < N; i++) {
        graph[i][i] = 0;
        for(int j = i + 1; j < N; j++) {
            graph[i][j] = graph[j][i] = mydis(g[i], g[j]);
        }
    }
}

int main() {
#ifndef ONLINE_JUDGE
    freopen("data.in", "r", stdin);
#endif
    while(scanf("%d", &N) == 1 && N > 0) {
        build_graph();
        printf("%.2f\n", MST_Prim());
    }
    return 0;
}
posted @ 2012-11-17 20:00  moonbay  阅读(307)  评论(0编辑  收藏  举报