hdu2489 Minimal Ratio Tree

hdu2489 Minimal Ratio Tree

题意:一个 至多  n=15 的 完全图 ,求 含有 m 个节点的树 使 边权和 除 点权和 最小

题解:枚举 m 个 点 ,然后 求 最小生成树

自己粗心。。。。WA 了 好多次……(233333 )

#include <iostream>

#include <cstring>

#include <cstdio>

#include <cmath>

#include <algorithm>

#include <vector>

#include <map>

#include <queue>

#include <stack>

#include <set>

#include <string>

using namespace std;

typedef long long ll;

const double ESP = 10e-8;

const int MOD = 1000000007;

typedef long long LL;

const int MAXN = 15 + 3;



int graph[MAXN][MAXN];

int node[MAXN];

int tmp[MAXN];

int dist[MAXN];

int ans[MAXN];

double ansMi;

int n,m;

bool vis[MAXN];

double prim(){

    double dis = 0;

    memset(vis,0,sizeof(vis));

    int cur = 0;

    vis[cur] = 1;

    for(int i = 0;i < m;i++){

        dist[i] = graph[ tmp[cur] ][ tmp[i] ];

    }



    for(int i = 0;i < m-1;i++){

        int mi = 0x7ffffff;

        int k;

        for(int j = 0;j < m;j++){

            if(!vis[j] && dist[j] < mi){

                mi = dist[j];

                k = j;

            }

        }

        cur = k;

        vis[cur] = 1;

        dis += mi;

        for(int j = 0;j < m;j++){

            if(!vis[j] && dist[j] > graph[ tmp[cur] ][ tmp[j] ]){

                dist[j] = graph[ tmp[cur] ][ tmp[j] ];

            }

        }

    }

    return dis;

}



void dfs(int v,int cnt){

    if(cnt == m-1){

        double h = 0;

        for(int i = 0;i < m;i++){

            h += node[ tmp[i] ];

        }

        double b = prim();

        double tt = b/h;

        if(tt - ansMi < -(1e-9)){

            ansMi = tt;

            for(int i = 0;i < m;i++){

                ans[i] = tmp[i];

            }

        }

        return;

    }

    for(int i = v+1;i<= n;i++){

        tmp[cnt+1] = i;

        dfs(i,cnt+1);

    }

}



int main(){

//    freopen("input.txt","r",stdin);

    while(~scanf("%d%d",&n,&m) && n &&m){

        for(int i = 1;i <= n;i++){

            scanf("%d",&node[i]);

        }

        for(int i = 1;i <= n;i++){

            for(int j = 1;j <= n;j++){

                scanf("%d",&graph[i][j]);

            }

        }

        ansMi = 10e10;

        for(int i = 1;i <= n;i++){

            tmp[0] = i;

            dfs(i,0);

        }

        for(int i = 0;i < m-1;i++){

            printf("%d ",ans[i]);

        }

        printf("%d\n",ans[m-1]);

    }

    return 0;

}

 

你可能感兴趣的:(tree)