NYOJ 118 次小生成樹

2021-08-26 10:01:20 字數 1882 閱讀 7600

先是prime演算法糾結了一天,,,,,然後這個次小生成樹又糾結了一天。本來昨天能搞出來的,,,昨天滿課,晚上又開會,,,就推到了今天上午,,,,在10點之前做了出來。。貢獻了幾次wr,,,,,不容易啊。。。深刻理解了prime,,寫次小生成樹時應該會容易一點點。

次小生成樹的兩種演算法:

演算法1、step 1. 先用prim求出最小生成樹t.

在prim的同時,用乙個矩陣max[u][v] 記錄 在t中鏈結任意兩點u,v的唯一的

路中權值最大的那條邊的權值. (注意這裡).

這是很容易做到的,因為prim是每次增加乙個結點s, 而設已經標號了的結點

集合為w, 則w中所有的結點到s的路中的最大權值的邊就是當前加入的這條邊.

step 1 用時 o(v^2).

step 2. 列舉所有不在t中的邊uv, 加入邊uv則必然替換權為max[u][v]的邊。

演算法2、先用prim求出最小生成樹t。

列舉t中的每一條邊,把它刪除,求剩下的圖的最小生成樹。選所有列舉得到的生成樹中的最小的那乙個。

題目:

時間限制:

3000ms | 記憶體限制:

65535kb

難度:5

描述

南將軍率領著許多部隊,它們分別駐紮在n個不同的城市裡,這些城市分別編號1~n,由於交通不太便利,南將軍準備修路。

現在已經知道哪些城市之間可以修路,如果修路,花費是多少。

現在,軍師小工已經找到了一種修路的方案,能夠使各個城市都聯通起來,而且花費最少。

但是,南將軍說,這個修路方案所拼成的圖案很不吉利,想讓小工計算一下是否存在另外一種方案花費和剛才的方案一樣,現在你來幫小工寫乙個程式算一下吧。

輸入

第一行輸入乙個整數t(1

輸出對於每組測試資料輸出yes或no(如果存在兩種以上的最小花費方案則輸出yes,如果最小花費的方案只有一種,則輸出no)

樣例輸入

2

3 31 2 1

2 3 2

3 1 3

4 41 2 2

2 3 2

3 4 2

4 1 2

樣例輸出

no

yes

ac**:

#include #include #include #include #include using namespace std;

const int n=505;

#define inf 1000005

int visted[n],map[n][n],f[n][n];

int use[n][n],key[n],pre[n];

int n,sum1,sum2;

void prime()

key[1]=0;

visted[1]=1;

int temp,pos=0;

sum1=0;

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

} if(temp==inf)

break;

use[pre[pos]][pos]=use[pos][pre[pos]]=0;

sum1+=temp;

visted[pos]=1;

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

} } }

void second_mst()}}}

int main()

prime();

second_mst();

if(sum1==sum2)

printf("yes\n");

else

printf("no\n");

} return 0;

}

nyoj 118 次小生成樹

描述 南將軍率領著許多部隊,它們分別駐紮在n個不同的城市裡,這些城市分別編號1 n,由於交通不太便利,南將軍準備修路。現在已經知道哪些城市之間可以修路,如果修路,花費是多少。現在,軍師小工已經找到了一種修路的方案,能夠使各個城市都聯通起來,而且花費最少。但是,南將軍說,這個修路方案所拼成的圖案很不吉...

nyoj118 修路方案 次小生成樹

如果已知最小生成樹,將未在生成樹的一條路徑加入生成樹必會產生乙個環,刪除環中除剛新增的一條以外的最大邊剩下的就是次小生成樹.求最小生成樹時用maxd陣列儲存兩點間最大的一條邊刪除時使用.include define inf 0x3f3f3f3f using namespace std const i...

NYOJ 118 Prim求次小生成樹

傳送門 思路 這裡用maxlen記錄在最小生成樹里的點兩點之間存在的最大的權值邊,然後列舉每條沒有加入的邊,如果有很這兩點之間在最小生成樹里的最大邊相等的,就說明有次小生成樹。include include include include include using namespace std de...