鍵.png)
使用這些基本 REST API 最佳實(shí)踐構(gòu)建出色的 API
圖1
然而現(xiàn)實(shí)世界中并不是所有的事物都可以表示成一個(gè)序列或者一個(gè)網(wǎng)格,例如社交網(wǎng)絡(luò)、知識(shí)圖譜、復(fù)雜的文件系統(tǒng)等(圖2),也就是說很多事物都是非結(jié)構(gòu)化的。
圖2
相比于簡單的文本和圖像,這種網(wǎng)絡(luò)類型的非結(jié)構(gòu)化的數(shù)據(jù)非常復(fù)雜,處理它的難點(diǎn)包括:
那么對于這類數(shù)據(jù)我們該如何建模呢?能否將深度學(xué)習(xí)進(jìn)行擴(kuò)展使得能夠建模該類數(shù)據(jù)呢?這些問題促使了圖神經(jīng)網(wǎng)絡(luò)的出現(xiàn)與發(fā)展。
相比較于神經(jīng)網(wǎng)絡(luò)最基本的網(wǎng)絡(luò)結(jié)構(gòu)全連接層(MLP),特征矩陣乘以權(quán)重矩陣,圖神經(jīng)網(wǎng)絡(luò)多了一個(gè)鄰接矩陣。計(jì)算形式很簡單,三個(gè)矩陣相乘再加上一個(gè)非線性變換(圖3)。
圖3
因此一個(gè)比較常見的圖神經(jīng)網(wǎng)絡(luò)的應(yīng)用模式如下圖(圖4),輸入是一個(gè)圖,經(jīng)過多層圖卷積等各種操作以及激活函數(shù),最終得到各個(gè)節(jié)點(diǎn)的表示,以便于進(jìn)行節(jié)點(diǎn)分類、鏈接預(yù)測、圖與子圖的生成等等任務(wù)。
圖4
上面是一個(gè)對圖神經(jīng)網(wǎng)絡(luò)比較簡單直觀的感受與理解,實(shí)際其背后的原理邏輯還是比較復(fù)雜的,這個(gè)后面再慢慢細(xì)說,接下來將以幾個(gè)經(jīng)典的GNN models為線來介紹圖神經(jīng)網(wǎng)絡(luò)的發(fā)展歷程。
GCN可謂是圖神經(jīng)網(wǎng)絡(luò)的“開山之作”,它首次將圖像處理中的卷積操作簡單的用到圖結(jié)構(gòu)數(shù)據(jù)處理中來,并且給出了具體的推導(dǎo),這里面涉及到復(fù)雜的譜圖理論,具體推導(dǎo)可以參考[6][7]。推導(dǎo)過程還是比較復(fù)雜的,然而最后的結(jié)果卻非常簡單( 圖5)。
圖5
我們來看一下這個(gè)式子,天吶,這不就是聚合鄰居節(jié)點(diǎn)的特征然后做一個(gè)線性變換嗎?沒錯(cuò),確實(shí)是這樣,同時(shí)為了使得GCN能夠捕捉到K-hop的鄰居節(jié)點(diǎn)的信息,作者還堆疊多層GCN layers,如堆疊K層有:
上述式子還可以使用矩陣形式表示如下,
其中 是歸一化之后的鄰接矩陣, 相當(dāng)于給 層的所有節(jié)點(diǎn)的embedding做了一次線性變換,左乘以鄰接矩陣表示對每個(gè)節(jié)點(diǎn)來說,該節(jié)點(diǎn)的特征表示為鄰居節(jié)點(diǎn)特征相加之后的結(jié)果。(注意將 換成矩陣 就是圖3所說的三矩陣相乘)
那么GCN的效果如何呢?作者將GCN放到節(jié)點(diǎn)分類任務(wù)上,分別在Citeseer、Cora、Pubmed、NELL等數(shù)據(jù)集上進(jìn)行實(shí)驗(yàn),相比于傳統(tǒng)方法提升還是很顯著的,這很有可能是得益于GCN善于編碼圖的結(jié)構(gòu)信息,能夠?qū)W習(xí)到更好的節(jié)點(diǎn)表示。
圖6
當(dāng)然,其實(shí)GCN的缺點(diǎn)也是很顯然易見的,第一,GCN需要將整個(gè)圖放到內(nèi)存和顯存,這將非常耗內(nèi)存和顯存,處理不了大圖;第二,GCN在訓(xùn)練時(shí)需要知道整個(gè)圖的結(jié)構(gòu)信息(包括待預(yù)測的節(jié)點(diǎn)), 這在現(xiàn)實(shí)某些任務(wù)中也不能實(shí)現(xiàn)(比如用今天訓(xùn)練的圖模型預(yù)測明天的數(shù)據(jù),那么明天的節(jié)點(diǎn)是拿不到的)。
為了解決GCN的兩個(gè)缺點(diǎn)問題,GraphSAGE被提了出來。在介紹GraphSAGE之前,先介紹一下Inductive learning和Transductive learning。注意到圖數(shù)據(jù)和其他類型數(shù)據(jù)的不同,圖數(shù)據(jù)中的每一個(gè)節(jié)點(diǎn)可以通過邊的關(guān)系利用其他節(jié)點(diǎn)的信息。這就導(dǎo)致一個(gè)問題,GCN輸入了整個(gè)圖,訓(xùn)練節(jié)點(diǎn)收集鄰居節(jié)點(diǎn)信息的時(shí)候,用到了測試和驗(yàn)證集的樣本,我們把這個(gè)稱為Transductive learning。然而,我們所處理的大多數(shù)的機(jī)器學(xué)習(xí)問題都是Inductive learning,因?yàn)槲覀兛桃獾膶颖炯譃橛?xùn)練/驗(yàn)證/測試,并且訓(xùn)練的時(shí)候只用訓(xùn)練樣本。這樣對圖來說有個(gè)好處,可以處理圖中新來的節(jié)點(diǎn),可以利用已知節(jié)點(diǎn)的信息為未知節(jié)點(diǎn)生成embedding,GraphSAGE就是這么干的。
GraphSAGE是一個(gè)Inductive Learning框架,具體實(shí)現(xiàn)中,訓(xùn)練時(shí)它僅僅保留訓(xùn)練樣本到訓(xùn)練樣本的邊,然后包含Sample和Aggregate兩大步驟,Sample是指如何對鄰居的個(gè)數(shù)進(jìn)行采樣,Aggregate是指拿到鄰居節(jié)點(diǎn)的embedding之后如何匯聚這些embedding以更新自己的embedding信息。下圖展示了GraphSAGE學(xué)習(xí)的一個(gè)過程。
圖7
第一步,對鄰居采樣;
第二步,采樣后的鄰居embedding傳到節(jié)點(diǎn)上來,并使用一個(gè)聚合函數(shù)聚合這些鄰居信息以更新節(jié)點(diǎn)的embedding;
第三步,根據(jù)更新后的embedding預(yù)測節(jié)點(diǎn)的標(biāo)簽;
接下來,我們詳細(xì)的說明一個(gè)訓(xùn)練好的GrpahSAGE是如何給一個(gè)新的節(jié)點(diǎn)生成embedding的(即一個(gè)前向傳播的過程),如下算法圖:
首先,(line1)算法首先初始化輸入的圖中所有節(jié)點(diǎn)的特征向量,(line3)對于每個(gè)節(jié)點(diǎn) ,拿到它采樣后的鄰居節(jié)點(diǎn) 后,(line4)利用聚合函數(shù)聚合鄰居節(jié)點(diǎn)的信息,(line5)并結(jié)合自身embedding通過一個(gè)非線性變換更新自身的embedding表示。
注意到算法里面的 ,它是指聚合器的數(shù)量,也是指權(quán)重矩陣的數(shù)量,還是網(wǎng)絡(luò)的層數(shù),這是因?yàn)槊恳粚泳W(wǎng)絡(luò)中聚合器和權(quán)重矩陣是共享的。網(wǎng)絡(luò)的層數(shù)可以理解為需要最大訪問的鄰居的跳數(shù)(hops),比如在圖7中,紅色節(jié)點(diǎn)的更新拿到了它一、二跳鄰居的信息,那么網(wǎng)絡(luò)層數(shù)就是2。為了更新紅色節(jié)點(diǎn),首先在第一層(k=1),我們會(huì)將藍(lán)色節(jié)點(diǎn)的信息聚合到紅色解節(jié)點(diǎn)上,將綠色節(jié)點(diǎn)的信息聚合到藍(lán)色節(jié)點(diǎn)上。在第二層(k=2)紅色節(jié)點(diǎn)的embedding被再次更新,不過這次用到的是更新后的藍(lán)色節(jié)點(diǎn)embedding,這樣就保證了紅色節(jié)點(diǎn)更新后的embedding包括藍(lán)色和綠色節(jié)點(diǎn)的信息,也就是兩跳信息。
為了看的更清晰,我們將更新某個(gè)節(jié)點(diǎn)的過程展開來看,如圖8分別為更新節(jié)點(diǎn)A和更新節(jié)點(diǎn)B的過程,可以看到更新不同的節(jié)點(diǎn)過程每一層網(wǎng)絡(luò)中聚合器和權(quán)重矩陣都是共享的。
圖8
那么GraphSAGE Sample是怎么做的呢?GraphSAGE是采用定長抽樣的方法,具體來說,定義需要的鄰居個(gè)數(shù) ,然后采用有放回的重采樣/負(fù)采樣方法達(dá)到 。保證每個(gè)節(jié)點(diǎn)(采樣后的)鄰居個(gè)數(shù)一致,這樣是為了把多個(gè)節(jié)點(diǎn)以及它們的鄰居拼接成Tensor送到GPU中進(jìn)行批訓(xùn)練。
那么GraphSAGE 有哪些聚合器呢?主要有三個(gè):
這里說明的一點(diǎn)是Mean Aggregator和GCN的做法基本是一致的(GCN實(shí)際上是求和)。
到此為止,整個(gè)模型的架構(gòu)就講完了,那么GraphSAGE是如何學(xué)習(xí)聚合器的參數(shù)以及權(quán)重矩陣 呢?如果是有監(jiān)督的情況下,可以使用每個(gè)節(jié)點(diǎn)的預(yù)測lable和真實(shí)lable的交叉熵作為損失函數(shù)。如果是在無監(jiān)督的情況下,可以假設(shè)相鄰的節(jié)點(diǎn)的embedding表示盡可能相近,因此可以設(shè)計(jì)出如下的損失函數(shù):
那么GrpahSAGE的實(shí)際實(shí)驗(yàn)效果如何呢?作者在Citation、Reddit、PPI數(shù)據(jù)集上分別給出了無監(jiān)督和完全有監(jiān)督的結(jié)果,相比于傳統(tǒng)方法提升還是很明顯。
至此,GraphSAGE介紹完畢。我們來總結(jié)一下,GraphSAGE的一些優(yōu)點(diǎn):
(1)利用采樣機(jī)制,很好的解決了GCN必須要知道全部圖的信息問題,克服了GCN訓(xùn)練時(shí)內(nèi)存和顯存的限制,即使對于未知的新節(jié)點(diǎn),也能得到其表示;
(2)聚合器和權(quán)重矩陣的參數(shù)對于所有的節(jié)點(diǎn)是共享的;
(3)模型的參數(shù)的數(shù)量與圖的節(jié)點(diǎn)個(gè)數(shù)無關(guān),這使得GraphSAGE能夠處理更大的圖;
(4)既能處理有監(jiān)督任務(wù)也能處理無監(jiān)督任務(wù)。
(就喜歡這樣解決了問題,方法又簡潔,效果還好的idea!!!)
當(dāng)然,GraphSAGE也有一些缺點(diǎn),每個(gè)節(jié)點(diǎn)那么多鄰居,GraphSAGE的采樣沒有考慮到不同鄰居節(jié)點(diǎn)的重要性不同,而且聚合計(jì)算的時(shí)候鄰居節(jié)點(diǎn)的重要性和當(dāng)前節(jié)點(diǎn)也是不同的。
為了解決GNN聚合鄰居節(jié)點(diǎn)的時(shí)候沒有考慮到不同的鄰居節(jié)點(diǎn)重要性不同的問題,GAT借鑒了Transformer的idea,引入masked self-attention機(jī)制,在計(jì)算圖中的每個(gè)節(jié)點(diǎn)的表示的時(shí)候,會(huì)根據(jù)鄰居節(jié)點(diǎn)特征的不同來為其分配不同的權(quán)值。
具體的,對于輸入的圖,一個(gè)graph attention layer如圖9所示:
圖9
其中 采用了單層的前饋神經(jīng)網(wǎng)絡(luò)實(shí)現(xiàn),計(jì)算過程如下(注意權(quán)重矩陣 對于所有的節(jié)點(diǎn)是共享的):
計(jì)算完attention之后,就可以得到某個(gè)節(jié)點(diǎn)聚合其鄰居節(jié)點(diǎn)信息的新的表示,計(jì)算過程如下:
為了提高模型的擬合能力,還引入了多頭的self-attention機(jī)制,即同時(shí)使用多個(gè) 計(jì)算self-attention,然后將計(jì)算的結(jié)果合并(連接或者求和):
此外,由于GAT結(jié)構(gòu)的特性,GAT無需使用預(yù)先構(gòu)建好的圖,因此GAT既適用于Transductive Learning,又適用于Inductive Learning。
那么GAT的具體效果如何呢?作者分別在三個(gè)Transductive Learning和一個(gè)Inductive Learning任務(wù)上進(jìn)行實(shí)驗(yàn),實(shí)驗(yàn)結(jié)果如下:
無論是在Transductive Learning還是在Inductive Learning的任務(wù)上,GAT的效果都要優(yōu)于傳統(tǒng)方法的結(jié)果。
至此,GAT的介紹完畢,我們來總結(jié)一下,GAT的一些優(yōu)點(diǎn):
(1)訓(xùn)練GCN無需了解整個(gè)圖結(jié)構(gòu),只需知道每個(gè)節(jié)點(diǎn)的鄰居節(jié)點(diǎn)即可;
(2)計(jì)算速度快,可以在不同的節(jié)點(diǎn)上進(jìn)行并行計(jì)算;
(3)既可以用于Transductive Learning,又可以用于Inductive Learning,可以對未見過的圖結(jié)構(gòu)進(jìn)行處理。
(仍然是簡單的idea,解決了問題,效果還好!!!)
到此,我們就介紹完了GNN中最經(jīng)典的幾個(gè)模型GCN、GraphSAGE、GAT,接下來我們將針對具體的任務(wù)類別來介紹一些流行的GNN模型與方法。
由于標(biāo)注數(shù)據(jù)的成本非常高,如果能夠利用無監(jiān)督的方法很好的學(xué)習(xí)到節(jié)點(diǎn)的表示,將會(huì)有巨大的價(jià)值和意義,例如找到相同興趣的社區(qū)、發(fā)現(xiàn)大規(guī)模的圖中有趣的結(jié)構(gòu)等等。
圖10
這其中比較經(jīng)典的模型有GraphSAGE、Graph Auto-Encoder(GAE)等,GraphSAGE就是一種很好的無監(jiān)督表示學(xué)習(xí)的方法,前面已經(jīng)介紹了,這里就不贅述,接下來將詳細(xì)講解后面兩個(gè)。
在介紹Graph Auto-Encoder之前,需要先了解自編碼器(Auto-Encoder)、變分自編碼器(Variational Auto-Encoder),具體可以參考[11],這里就不贅述。
理解了自編碼器之后,再來理解變分圖的自編碼器就容易多了。如圖11輸入圖的鄰接矩陣和節(jié)點(diǎn)的特征矩陣,通過編碼器(圖卷積網(wǎng)絡(luò))學(xué)習(xí)節(jié)點(diǎn)低維向量表示的均值μ和方差σ,然后用解碼器(鏈路預(yù)測)生成圖。
圖11
編碼器(Encoder)采用簡單的兩層GCN網(wǎng)絡(luò),解碼器(Encoder)計(jì)算兩點(diǎn)之間存在邊的概率來重構(gòu)圖,損失函數(shù)包括生成圖和原始圖之間的距離度量,以及節(jié)點(diǎn)表示向量分布和正態(tài)分布的KL-散度兩部分。具體公式如圖12所示:
圖12
另外為了做比較,作者還提出了圖自編碼器(Graph Auto-Encoder),相比于變分圖的自編碼器,圖自編碼器就簡單多了,Encoder是兩層GCN,Loss只包含Reconstruction Loss。
那么兩種圖自編碼器的效果如何呢?作者分別在Cora、Citeseer、Pubmed數(shù)據(jù)集上做Link prediction任務(wù),實(shí)驗(yàn)結(jié)果如下表,圖自編碼器(GAE)和變分圖自編碼器(VGAE)效果普遍優(yōu)于傳統(tǒng)方法,而且變分圖自編碼器的效果更好;當(dāng)然,Pumed上GAE得到了最佳結(jié)果。可能是因?yàn)镻umed網(wǎng)絡(luò)較大,在VGAE比GAE模型復(fù)雜,所以更難調(diào)參。
Graph pooling是GNN中很流行的一種操作,目的是為了獲取一整個(gè)圖的表示,主要用于處理圖級別的分類任務(wù),例如在有監(jiān)督的圖分類、文檔分類等等。
圖13
Graph pooling的方法有很多,如簡單的max pooling和mean pooling,然而這兩種pooling不高效而且忽視了節(jié)點(diǎn)的順序信息;這里介紹一種方法:Differentiable Pooling (DiffPool)。
在圖級別的任務(wù)當(dāng)中,當(dāng)前的很多方法是將所有的節(jié)點(diǎn)嵌入進(jìn)行全局池化,忽略了圖中可能存在的任何層級結(jié)構(gòu),這對于圖的分類任務(wù)來說尤其成問題,因?yàn)槠淠繕?biāo)是預(yù)測整個(gè)圖的標(biāo)簽。針對這個(gè)問題,斯坦福大學(xué)團(tuán)隊(duì)提出了一個(gè)用于圖分類的可微池化操作模塊——DiffPool,可以生成圖的層級表示,并且可以以端到端的方式被各種圖神經(jīng)網(wǎng)絡(luò)整合。
DiffPool的核心思想是通過一個(gè)可微池化操作模塊去分層的聚合圖節(jié)點(diǎn),具體的,這個(gè)可微池化操作模塊基于GNN上一層生成的節(jié)點(diǎn)嵌入 以及分配矩陣 ,以端到端的方式分配給下一層的簇,然后將這些簇輸入到GNN下一層,進(jìn)而實(shí)現(xiàn)用分層的方式堆疊多個(gè)GNN層的想法。(圖14)
圖14
那么這個(gè)節(jié)點(diǎn)嵌入和分配矩陣是怎么算的?計(jì)算完之后又是怎么分配給下一層的?這里就涉及到兩部分內(nèi)容,一個(gè)是分配矩陣的學(xué)習(xí),一個(gè)是池化分配矩陣。
這里使用兩個(gè)分開的GNN來生成分配矩陣 和每一個(gè)簇節(jié)點(diǎn)新的嵌入 ,這兩個(gè)GNN都是用簇節(jié)點(diǎn)特征矩陣 和粗化鄰接矩陣 作為輸入:
計(jì)算得到分配矩陣 和每一個(gè)簇節(jié)點(diǎn)新的嵌入 之后,DiffPool層根據(jù)分配矩陣,對于圖中的每個(gè)節(jié)點(diǎn)/簇生成一個(gè)新的粗化的鄰接矩陣 與新的嵌入矩陣 :
總的來看,每層的DiffPool其實(shí)就是更新每一個(gè)簇節(jié)點(diǎn)的嵌入和簇節(jié)點(diǎn)的特征矩陣,如下公式:
至此,DiffPool的基本思想就講完了。那么效果如何呢?作者在多種圖分類的基準(zhǔn)數(shù)據(jù)集上進(jìn)行實(shí)驗(yàn),如蛋白質(zhì)數(shù)據(jù)集(ENZYMES,PROTEINS,D&D),社交網(wǎng)絡(luò)數(shù)據(jù)集(REDDIT-MULTI-12K),科研合作數(shù)據(jù)集(COLLAB),實(shí)驗(yàn)結(jié)果如下:
其中,GraphSAGE是采用全局平均池化;DiffPool-DET是一種DiffPool變體,使用確定性圖聚類算法生成分配矩陣;DiffPool-NOLP是DiffPool的變體,取消了鏈接預(yù)測目標(biāo)部分。總的來說,DiffPool方法在GNN的所有池化方法中獲得最高的平均性能。
為了更好的證明DiffPool對于圖分類十分有效,論文還使用了其他GNN體系結(jié)構(gòu)(Structure2Vec(s2v)),并且構(gòu)造兩個(gè)變體,進(jìn)行對比實(shí)驗(yàn),如下表:
可以看到DiffPool的顯著改善了S2V在ENZYMES和D&D數(shù)據(jù)集上的性能。
而且DiffPool可以自動(dòng)的學(xué)習(xí)到恰當(dāng)?shù)拇氐臄?shù)量。
至此,我們來總結(jié)一下DiffPool的優(yōu)點(diǎn):
(1)可以學(xué)習(xí)層次化的pooling策略;
(2)可以學(xué)習(xí)到圖的層次化表示;
(3)可以以端到端的方式被各種圖神經(jīng)網(wǎng)絡(luò)整合。
然而,注意到,DiffPool也有其局限性,分配矩陣需要很大的空間去存儲(chǔ),空間復(fù)雜度為 , 為池化層的層數(shù),所以無法處理很大的圖。
【1】^Graph Neural Networks: A Review of Methods and Applications. arxiv 2018 https://arxiv.org/pdf/1812.08434.pdf
【2】^A Comprehensive Survey on Graph Neural Networks. arxiv 2019. https://arxiv.org/pdf/1901.00596.pdf
【3】^Deep Learning on Graphs: A Survey. arxiv 2018. https://arxiv.org/pdf/1812.04202.pdf
【4】^GNNpapers https://github.com/thunlp/GNNPapers/blob/master/README.md
【5】^Semi-Supervised Classification with Graph Convolutional Networks(ICLR2017) https://arxiv.org/pdf/1609.02907
【6】^如何理解 Graph Convolutional Network(GCN)?https://www.zhihu.com/question/54504471
【7】^GNN 系列:圖神經(jīng)網(wǎng)絡(luò)的“開山之作”CGN模型 https://mp.weixin.qq.com/s/jBQOgP-I4FQT1EU8y72ICA
【8】^Inductive Representation Learning on Large Graphs(2017NIPS) https://cs.stanford.edu/people/jure/pubs/graphsage-nips17.pdf
【9】^Graph Attention Networks(ICLR2018) https://arxiv.org/pdf/1710.10903
【10】^Variational Graph Auto-Encoders(NIPS2016) https://arxiv.org/pdf/1611.07308
【11】^VGAE(Variational graph auto-encoders)
論文詳解 https://zhuanlan.zhihu.com/p/78340397
【12】^Hierarchical Graph Representation Learning withDifferentiable Pooling(NIPS2018) https://arxiv.org/pdf/1806.08
1. GCN的缺點(diǎn)也是很顯然易見的:
第一,GCN需要將整個(gè)圖放到內(nèi)存和顯存,這將非常耗內(nèi)存和顯存,處理不了大圖;
第二,GCN在訓(xùn)練時(shí)需要知道整個(gè)圖的結(jié)構(gòu)信息(包括待預(yù)測的節(jié)點(diǎn))。
2. GraphSAGE的優(yōu)點(diǎn):
(1)利用采樣機(jī)制,很好的解決了GCN必須要知道全部圖的信息問題,克服了GCN訓(xùn)練時(shí)內(nèi)存和顯存的限制,即使對于未知的新節(jié)點(diǎn),也能得到其表示;
(2)聚合器和權(quán)重矩陣的參數(shù)對于所有的節(jié)點(diǎn)是共享的;
(3)模型的參數(shù)的數(shù)量與圖的節(jié)點(diǎn)個(gè)數(shù)無關(guān),這使得GraphSAGE能夠處理更大的圖;(4)既能處理有監(jiān)督任務(wù)也能處理無監(jiān)督任務(wù)。
3.GAT的優(yōu)點(diǎn):
(1)訓(xùn)練GCN無需了解整個(gè)圖結(jié)構(gòu),只需知道每個(gè)節(jié)點(diǎn)的鄰居節(jié)點(diǎn)即可;
(2)計(jì)算速度快,可以在不同的節(jié)點(diǎn)上進(jìn)行并行計(jì)算;
(3)既可以用于Transductive Learning,又可以用于Inductive Learning,可以對未見過的圖結(jié)構(gòu)進(jìn)行處理。
文章轉(zhuǎn)自微信公眾號(hào)@算法進(jìn)階