最小生成树

最小生成树:如果边上有权值,那么使得边权值和最小的生成树叫做最小生成树。

1.最小生成树问题1(Prim算法)
int cost[maxn][maxn];   //cost[u][v]表示边e = (u, v)的权值(不存在的情况下设为INF)
int mincost[maxn];   //从集合x出发的边到每个顶点的最小权值
bool used[maxn];   //顶点i是否包含在集合x中
int V;   //顶点数

int prim()
{
    for (int i = 0; i < V; i++){
        mincost[i] = INF;
        used[i] = false;
    }
    mincost[0] = 0;
    int res = 0;
    
    while (true){
        int v = -1;
        //从不属于x的顶点中选取从x到其权值最小的顶点
        for (int u = 0; u < V; u++){
            if (!used[u] && (v == -1 || mincost[u] < mincost[v]))
                v = u;
        }
        
        if (v == -1)
            break;
        used[v] = true;  //把顶点v加入x
        res += mincost[v];   //把边的长度加入到结果里
        for (int u = 0; u < V; u++){
            mincost[u] = min(mincost[u], cost[v][u]);
        }
    }
    return res;
}

2.最小生成树问题2(Kruskal算法)
Kruskal算法按照边的权值的顺序从小到大查看一遍,如果不产生圈(重边等也算在内),
就把当前这条边加入到生成树中。

struct edge { int u, v, cost; };

bool comp(const edge& e1, const edge& e2)
{
    return e1.cost < e2.cost;
}

edge es[maxn];
int V, E;   //顶点数和边数

int Kruskal()
{
    sort(es, es + E, comp);   //按照edge.cost的顺序从小到大排列
    init_union_find(V);   //并查集的初始化
    int res = 0;
    for (int i = 0; i < E; i++){
        edge e = es[i];
        if (!same(e.u, e.u)){
            unite(e,u, e.v);
            res += e.cost;
        }
    }
    return res;
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值