图论(六)图的两种表示方法
如果要用圖來解決問題,首先我們必須采用某種數據結構來存儲和表示“圖”。相對于數組、鏈表等來說,圖的存儲結構就復雜的多了。
- 首先,圖上的任何一個頂點都可以被看作是第一個頂點,任意頂點的鄰接頂點之間也不存在次序關系。還記得在《圖論(一)基本概念》中的“同構圖”吧,圖的形狀可以千變萬化的。因此也就無法以數據元素在內存中的物理位置來表示元素之間的關系,也就是說,圖不可能用數組這樣簡單的順序存儲結構來表示。
- 其次,如果使用鏈表一樣的鏈式存儲結構,不同頂點的鄰接頂點數量是不一樣的,相差可能很大,如何在操作和效率之間尋求平衡是個大難題。
不過不用擔心,計算機科學界不缺乏牛人,前輩們早就為我們設計好了,而且方法不止一種,發明了大量的圖表示法,甚至還有專門從事圖表示法的研究員(Jeremy P.Spinrad),還寫過一本書《Efficient Graph Representations》。
盡管有大量的圖表示法可用,但我們需要掌握的,也是最常用的、最著名的,可用性和普及率都最高的,只有兩類:鄰接表法和鄰接矩陣法。都帶有“鄰接”兩字,這是數學語言,大白話的意思就是“鄰居”。
(1)鄰接表
鄰接表的核心思想就是針對每個頂點設置一個鄰居表。
以上面的圖為例,這是一個有向圖,分別有頂點a, b, c, d, e, f, g, h共8個頂點。使用鄰接表就是針對這8個頂點分別構建鄰居表,從而構成一個8個鄰居表組成的結構,這個結構就是我們這個圖的表示結構或者叫存儲結構。
這樣,N構成了一個鄰居節點集。可以通過N對圖進行操作了。
# 頂點f的鄰居頂點 print(N[f]) # 頂點g是否是a的鄰居頂點 print(g in N[a]) # 頂點a的鄰居頂點個數 print(len(N[a]))輸出結果:
{2, 6, 7} False 5注意:每個頂點的鄰居表都是一個集合(set),為什么用set,因為不能重復存儲鄰居頂點,這是一個非常自然的選擇。那么,可不可以用list,當然可以。用字典呢,當然也可以,甚至在表示帶權重值的圖時,使用字典表示更合理。
N = [{b: 1, c: 2, d: 1, e: 2, f: 3}, # a 的鄰居表{c: 1, e: 2}, # b 的鄰居表{d: 3}, # c 的鄰居表{e: 1}, # d 的鄰居表{f: 2}, # e 的鄰居表{c: 1, g: 1, h: 1}, # f 的鄰居表{f: 1, h: 2}, # g 的鄰居表{f: 1, g: 2}] # h 的鄰居表# 邊(a,f)的權重 if f in N[a]:print(N[a][f])輸出結果:
3需要注意的是,不管鄰居表是用set,list,還是dict,都是鄰接表的各種變形,最終使用哪個取決于這個圖本身是什么,我們要用這個圖干什么。實際應用中我們可以針對圖本身特點和我們要解決問題特點針對性的構建圖的表示結構。
(2)鄰接矩陣
鄰接矩陣的核心思想是針對每個頂點設置一個表,這個表包含所有頂點,通過True/False來表示是否是鄰居頂點。
還是針對上面的圖,分別有頂點a, b, c, d, e, f, g, h共8個頂點。使用鄰接矩陣就是針對這8個頂點構建一個8×8的矩陣組成的結構,這個結構就是我們這個圖的表示結構或存儲結構。
同樣,可以對N進行圖操作了,操作方式與鄰接表方式有所不同。
# 頂點g是否是a的鄰居頂點 print(N[a][g])# 頂點a的鄰居頂點個數 print(sum(N[a]))# 頂點a的鄰居頂點 neighbour = [] for i in range(len(N[f])): if N[f][i]: neighbour.append(i) print(neighbour)輸出結果:
0 5 [2, 6, 7]在鄰接矩陣表示法中,有一些非常實用的特性。
- 首先,可以看出,該矩陣是一個方陣,方陣的維度就是圖中頂點的數量,同時還是一個對稱矩陣,這樣進行處理時非常方便。
- 其次,該矩陣對角線表示的是頂點與頂點自身的關系,一般圖不允許出現自關聯狀態,即自己指向自己的邊,那么對角線的元素全部為0;
- 最后,該表示方式可以不用改動即可表示帶權值的圖,直接將原來存儲1的地方修改成相應的權值即可。當然, 0也是權值的一種,而鄰接矩陣中0表示不存在這條邊。出于實踐中的考慮,可以對不存在的邊的權值進行修改,將其設置為無窮大或非法的權值,如None,-99999/99999等。
最后總結下,鄰接表和鄰接矩陣兩種表示方法各有特點,具體使用哪個應該針對具體問題具體分析。但事實上,如果不是特別巨大無比的圖,用不著費勁思考,用哪種都可以的。
總結
以上是生活随笔為你收集整理的图论(六)图的两种表示方法的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 图论(三)图的遍历
- 下一篇: 《生活随笔》相关内容将转移到个人微信公众