最小生成树

prim算法:

框架:

int  prim()
{
	int ans , min , pos = 0 , i , j ;
	//初始化标记数组。 
	memset(used,0,sizeof(used));
	used[0] = 1;
	//一第一个扩展点为扩展对象更新low数组
	for(int i = 0 ; i < n ; i++)
		if(i!=pos )  low[i] = map[pos][i];
	//循环,每循环一次 ans+=min min是最小边长。 
	for(i = 0 ; i < n-1 ; i++)   
	{ 
		//更新  min 和  当前点 pos 
		min = INF ;
		for(j = 0 ; j < n ; j++)
			if(used[j]==0 && min>low[j])
			{
				min = low [j];
				pos = j;
			} 
		//处理 
		use[pos] = 1;
		ans += min;		
		//以  节点pos  为扩展对象更新  low数组。 
		for(j = 0 ; j < n ; j++ )
		 	if(used[i]==0 && low[j]>map[pos][j])
			 	low[j] = map[pos][j];		
	}
	return ans ;
}


poj1258代码:

#include<stdio.h>
#include<iostream>
#define INF 0x3f3f3f3f
using namespace std;
int map[110][110],used[110],low[110],n;
int prim()
{
	int ans = 0 , min , i ,j , pos = 0;
	memset(used,0,sizeof(used));                   //初始化标记数组。 
	used[0] = 1;
	
	for( i = 0 ; i < n ; i++)                      //low数组一第一个节点为扩展节点进行初始化 
		if(i!=pos)  low[i] = map[pos][i];
	
	for( i = 0 ; i < n-1 ; i++)                      //没循环一次,ans+=min ; 共 n-1 条边。 
	{
		
		min = INF;                                 //更新	扩展边 min 
		for( j = 0 ; j < n ; j++)					
 			if(!used[j] && min>low[j])
			{
				min = low[j];
				pos = j;
			}
			
			
		ans += min ;								//ans + = min  ; 
		int cn;
	//	cout<<ans<<" "<<min<<endl;cin>>cn;
		used[pos] = 1;								//标记访问。 
		
		
		for( j = 0 ; j < n ; j++)                   //更新 low数组。 
			if(!used[j] && low[j]>map[pos][j])
				low[j] = map[pos][j];
	} 
	return ans;
}
int main()
{
	while(cin>>n)
	{
		for(int i = 0 ; i < n ; i++)
			for(int j = 0 ; j < n ; j++)
				cin>>map[i][j];
		int ans;
		ans = prim();
		cout<<ans<<endl;
	}
	return 0;
}

杭电1233:

prim算法:
#include<stdio.h>
#include<iostream>
#define INF 0x3f3f3f3f
using namespace std;
int n,map[110][110],used[110],low[110];
int prim()
{
    int ans = 0 , pos = 1 ,min , i , j ;
    memset(used,0,sizeof(used));
    used[1] = 1 ;
    for(i = 1 ; i<= n ;i++)
        if(i!=pos)low[i]=map[pos][i];
//    for(i=1;i<=n;i++)cout<<low[i]<<"   ";cout<<endl;
    for(i = 1 ; i< n ; i++)
    {
        min=INF;
        for(j = 1 ;j<=n ; j++)
            if(!used[j] && min>low[j])
            {
                min=low[j];
                pos = j;
            }
            
        used[pos] = 1;
        ans += min;        //    cout<<min<<" "<<ans<<endl;
        
        for(j=1;j<=n;j++)
            if(used[j]==0 && low[j]>map[pos][j])
                low[j]=map[pos][j];
    }
    return ans;
}
int main()
{
    while(cin>>n)
    {
        if(n==0)break;
        int a,b,c;
        for(int i = 1 ; i <= n*(n-1)/2 ; i++)
        {
            cin>>a>>b>>c;
            map[a][b]=map[b][a]=c;
        }
    /*    for(int i = 1 ; i <= n ; i++)
        {
            for(int j = 1 ; j <= n ; j++)            
                cout<<map[i][j]<<" ";
            cout<<endl;
        }
        */
        int ans ;
        ans = prim();
        cout<<ans<<endl;
    }
    return 0;
} 


  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值