哈密頓迴路

2022-04-07 09:26:47 字數 2595 閱讀 9075

哈密頓迴路好多,其實不是很難,但是看了一天了。。看一會睡一會,什麼狀態啊。。 

view code

/*

【題目**】

【題目分析】

有敵對關係的小朋友,不能坐在一起。最後圍成乙個圈,吃飯。。。

將小朋友看成點,有敵對關係的看成沒有邊,最後構成乙個迴路。

哈密頓迴路。

【小小總結】

哈密頓迴路

充分條件:

無向連通圖中任意2點度數之和大於等於頂點數,則必定存在哈密頓迴路。

思路分析:

1.任意找兩個相鄰的節點s和t,在它們基礎上擴充套件出一條盡量長的沒有重複節點的路徑。

也就是說,如果s與節點v相鄰,而且v不在路徑s->t上,則可以把該路徑變成v->s->t,然後v成為新的s。

從s和t分別向兩頭擴充套件,直到無法擴為止,即所有與s或t相鄰的節點都在路徑s->t上。

2.若s與t相鄰,則路徑s->t形成了乙個迴路。

3.若s與t不相鄰,可以構造出乙個迴路。設路徑s->t上有k+2個節點,依次為s、v1、v2……vk和t。

可以證明v1到vk中必定存在vi,滿足vi與t相鄰,且vi+1與s相鄰。(其實vi,vi+1與s t同時相鄰) (怎麼證明就不贅述了,反正刷題肯定不會叫你證)

找到了滿足條件的節點vi以後,就可以把原路徑變成s->vi+1->t->vi->s,即形成了乙個迴路。(自己畫圖就知道了)

4.現在我們有了乙個沒有重複節點的迴路。如果它的長度為n,則哈密頓迴路就找到了。

如果迴路的長度小於n,由於整個圖是連通的,所以在該回路上,一定存在一點與迴路以外的點相鄰。

那麼從該點處把迴路斷開,就變回了一條路徑。再按照步驟1的方法盡量擴充套件路徑,則一定有新的節點被加進來。(畫圖就知道了)

接著回到步驟2。

偽**:

思路清楚後主要是理解好偽**,偽**一懂**就寫出來了。關於下面步驟中為什麼要倒置,自己畫畫圖就清楚了。

s為哈密頓迴路起點,t為當前哈密頓迴路的終點,ans就是哈密頓迴路啦,預設不包含0頂點

1.初始化,令s=1,t為任意與s相鄰的點。

2.若ans中的元素個數小於n,則從t開始擴充套件,若可擴充套件,則把新點v加入ans,並令t=v,繼續擴充套件到無法擴充套件。

3.將ans倒置,s,t互換,從t(原來的s)開始擴充套件,若可擴充套件,則把新點v加入ans,並令t=v,繼續擴充套件到無法擴充套件。

4.此時s,t兩頭都無法擴充套件了,若s,t相連,則繼續步驟5。若st不相連,則遍歷ans,必定會有2點,ans[i]與t相連,ans[i+1]與s相連,

將ans[i+1]到t倒置,t=ans[i+1](未倒置前的)

5.st相連,此時為乙個環。若ans個數等於n,演算法結束,ans為哈密頓迴路,如需要再新增乙個起點。

若ans個數小於n,遍歷ans,尋找ans[i],使得ans[i]與ans外一點j相連,倒置ans中s到ans[i-1]部分,令s = ans[i-1],

再倒置ans中ans[i]到t的部分,j加入ans,t = j.繼續步驟2

下面去掉main函式,就是求解哈密頓迴路的模版了。

*/#include

#include

#include

using

namespace

std;

#define max 500

intmap[max][max];

intans[max];

bool

vis[max];

//ans陣列的index

intindex;

intn, m;

ints, t;

void

init()

void reverse(int a, intb)}

void

expand()

}if (i > n) break;//

無法擴充套件 }}

void

hamilton()

}vis[s] = true

;

vis[t] = true

;

ans[index++] =s;

ans[index++] =t;

while (true

) }}

//若ans元素有n個,說明演算法完成

if (index == n) return

;

//若ans元素不滿n個,ans中尋找與未被遍歷過的點相連的點,但這一點必定不是s,t.因為s,t已經遍歷到無法遍歷才能走到這一步

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

}if (map[ans[i]][j])break;//

記得有2個迴圈,要break兩次

} }

//繼續返回,從t擴充套件。。 }}

intmain()

hamilton();

cout

<< ans[0

];

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

cout

<< '

'<

cout

<

}}

哈密頓迴路

圖類 include include include include includeusing namespace std template t為頂點的資料型別,e為圖中邊的權值的資料型別 class graph 返回最大頂點數 int numberofedges 返回當前邊數 t getvalue...

哈密頓迴路

quad 設無向圖 g v,e 其中 v 是點集,e 是邊集,n v 表示圖中點的數量,m e 表示圖中邊的數量。hamilton 通路 quad 經過圖 g 中每個節點一次且僅一次的通路稱為 hamilton 通路 hamilton 迴路 quad 經過圖 g 中每個節點一次且僅一次的通路稱為 h...

最小哈密頓迴路

老楊留的作業,折騰幾個小時加上參考別人的終於寫出來了,還是很弱啊。效率貌似還可以,強化了分支定界的條件之後計算n 20的情況只需要十幾秒。好好體會一下 include include include include using namespace std define n 15 int curlig...