kruskal算法(最常用):(复杂度取决于边)
#include<stdio.h>
#include<iostream>
#include<algorithm>
#include<string.h>
#include<vector>
#include<cmath>
#include<string>
#include<map>
using namespace std;
typedef long long ll;
struct node{
ll x,y,z;
}dp[1000];
int cmp(node a,node b){
if(a.z==b.z){
if(a.x==b.x)
return a.y<b.y;
return a.x<b.x;
}
return a.z<b.z;
}
ll f[1000];
ll find(ll x){
ll r=x;
while(r!=f[r]){
r=f[r];
}
ll j=x;
while(f[j]!=r){
x=f[j];
f[j]=r;
j=x;
}
return r;
}
int main(){
ll n,m;
while(cin>>n>>m&&n){
for(int i=1;i<=m;i++){
f[i]=i;
}
for(int i=0;i<n;i++){
cin>>dp[i].x>>dp[i].y>>dp[i].z;
}
sort(dp,dp+n,cmp);
ll cnt=0,sum=0;
for(int i=0;i<n;i++){
ll tx=find(dp[i].x);
ll ty=find(dp[i].y);
if(tx!=ty){
f[tx]=ty;
cnt++;
sum+=dp[i].z;
if(cnt==m-1)
break;
}
}
if(cnt==m-1){
cout<<sum<<endl;
}
else cout<<"?"<<endl;
}
return 0;
}
prim(复杂度n*n):
#include<stdio.h>
#include<iostream>
#include<algorithm>
#include<string.h>
#include<vector>
#include<cmath>
#include<string>
#include<map>
using namespace std;
typedef long long ll;
#define INF 0x3f3f3f3f
ll dp[51][51],dis[51],flag[51];
int main(){
ll t,n;
while(cin>>n&&n){
memset(flag,0,sizeof(flag));
cin>>t;
for(int i=1;i<=n;i++){
for(int j=1;j<=n;j++){
if(i==j)
dp[i][i]=0;
else dp[i][j]=INF;
}
}
for(int i=0;i<t;i++){
ll x,y,z;
cin>>x>>y>>z;
dp[x][y]=dp[y][x]=min(dp[x][y],z);
}
dis[1]=0;
flag[1]=1;
for(int i=2;i<=n;i++){
dis[i]=dp[1][i];
}
ll sum=0;
for(int i=1;i<n;i++){
ll min_s=INF,index;
for(int j=1;j<=n;j++){
if(!flag[j]&&min_s>dis[j]){
min_s=dis[j];
index=j;
}
}
sum+=dis[index];
flag[index]=1;
for(int k=1;k<=n;k++){
if(!flag[k]&&dis[k]>dp[index][k]){
dis[k]=dp[index][k];
}
}
}
cout<<sum<<endl;
}
return 0;
}