小男孩‘自慰网亚洲一区二区,亚洲一级在线播放毛片,亚洲中文字幕av每天更新,黄aⅴ永久免费无码,91成人午夜在线精品,色网站免费在线观看,亚洲欧洲wwwww在线观看

分享

(3)映射二分堆實(shí)現(xiàn)prim最小生成樹模板

 dongsibei 2014-04-24

//無向圖最小生成樹,prim算法+映射二分堆,鄰接表形式,復(fù)雜度O(mlogn)
//返回最小生成樹的長度,傳入圖的大小n和鄰接表list
//可更改邊權(quán)的類型,pre[]返回樹的構(gòu)造,用父結(jié)點(diǎn)表示,根節(jié)點(diǎn)(第一個(gè))pre值為-1
//必須保證圖的連通的!
#include <iostream>
#include <cstring>
#include <cstdio>
#include <cstdlib>
#include <ctime>
using namespace std;

#define MAXN 200
#define inf 1000000000
typedef double elem_t;
struct edge_t{
 int from,to;
 elem_t len;
 edge_t* next;
};


#define _cp(a,b) ((a)<(b))
struct heap{
 elem_t h[MAXN+1];
 int ind[MAXN+1],map[MAXN+1],n,p,c;
 void init(){n=0;}
 void ins(int i,elem_t e){
  //插入第i個(gè)數(shù)到堆中
  for (p=++n;p>1&&_cp(e,h[p>>1]);h[map[ind[p]=ind[p>>1]]=p]=h[p>>1],p>>=1);
  h[map[ind[p]=i]=p]=e;
 }
 //從堆中刪除第i個(gè)數(shù)
 int del(int i,elem_t& e){
  i=map[i];if (i<1||i>n) return 0;
  for (e=h[p=i];p>1;h[map[ind[p]=ind[p>>1]]=p]=h[p>>1],p>>=1); 
  for (c=2;c<n&&_cp(h[c+=(c<n-1&&_cp(h[c+1],h[c]))],h[n]);h[map[ind[p]=ind[c]]=p]=h[c],p=c,c<<=1);
  h[map[ind[p]=ind[n]]=p]=h[n];n--;return 1;
 }
 //從堆中刪除最小的數(shù),并返回改最小值的原始下標(biāo)i
 int delmin(int& i,elem_t& e){
  if (n<1) return 0;i=ind[1];
  for (e=h[p=1],c=2;c<n&&_cp(h[c+=(c<n-1&&_cp(h[c+1],h[c]))],h[n]);h[map[ind[p]=ind[c]]=p]=h[c],p=c,c<<=1);
  h[map[ind[p]=ind[n]]=p]=h[n];n--;return 1;
 }
};

elem_t prim(int n,edge_t list[],int* pre){
 heap h;
 elem_t min[MAXN],ret=0,e;
 edge_t* t;
 int v[MAXN],i;
 for (h.init(),i=0;i<n;i++)
  min[i]=(i?inf:0),v[i]=0,pre[i]=-1,h.ins(i,min[i]);
 while (h.delmin(i,e))
  for (v[i]=1,ret+=e,t=list[i].next;t;t=t->next)
   if (!v[t->to]&&t->len<min[t->to])
    pre[t->to]=t->from,h.del(t->to,e),h.ins(t->to,min[t->to]=t->len);
 return ret;
}

//初始化連接表
void Init(edge_t list[],int n)
{
 int i;
 for (i = 0; i < n; i ++)
  list[i].next = NULL;
}
edge_t* FindEnd(edge_t* list)
{
 edge_t* p = list;
 while(p && p->next != NULL)
  p = p->next;
 return p;
}
void CreateLink(edge_t list[],int m,int n)
{
 edge_t* end;
 edge_t* p;
 Init(list,n);
 int i,x,y,z;
 for (i = 0; i < m; i ++)
 {
  scanf("%d%d%d",&x,&y,&z);
  end = FindEnd(list[x].next);//查找鏈表的最后一個(gè)節(jié)點(diǎn)
  p = (edge_t*)malloc(sizeof(edge_t));
  p->from = x;
  p->to = y;
  p->len = z;
  p->next = NULL;
  if (!end)
   list[x].next = p;
  else
   end->next = p;
  end = FindEnd(list[y].next);//查找鏈表的最后一個(gè)節(jié)點(diǎn)
  p = (edge_t*)malloc(sizeof(edge_t));
  p->from = y;
  p->to = x;
  p->len = z;
  p->next = NULL;
  if (!end)
   list[y].next = p;
  else
   end->next = p;
 }
}
int main(void)
{
 clock_t start,finish;
 start = clock();
 freopen("最小生成樹(kruskal鄰接表形式).txt","r",stdin);
 edge_t list[MAXN];
 int pre[MAXN];
 int n,m,i;
 scanf("%d%d",&n,&m);
 CreateLink(list,m,n);
 double ans = prim(n,list,pre);
 cout << ans << endl;
 for (i = 1; i < n; i ++)
  cout << pre[i] << "---" << i << endl;
 finish = clock();
 cout << (finish - start) / CLOCKS_PER_SEC << "ms" << endl;
 return 0;
}

    本站是提供個(gè)人知識(shí)管理的網(wǎng)絡(luò)存儲(chǔ)空間,所有內(nèi)容均由用戶發(fā)布,不代表本站觀點(diǎn)。請(qǐng)注意甄別內(nèi)容中的聯(lián)系方式、誘導(dǎo)購買等信息,謹(jǐn)防詐騙。如發(fā)現(xiàn)有害或侵權(quán)內(nèi)容,請(qǐng)點(diǎn)擊一鍵舉報(bào)。
    轉(zhuǎn)藏 分享 獻(xiàn)花(0

    0條評(píng)論

    發(fā)表

    請(qǐng)遵守用戶 評(píng)論公約