一.文章概述
本文提出了一种自监督属性图生成任务来预训练GNN,使得其能捕图的结构和语义属性。作者将图的生成分为两个部分:属性生成和边生成,即给定观测到的边,生成节点属性;给定观测到的边和生成的节点属性,生成剩余的边。通过这种方式使得模型能捕获每个节点属性和结构之间的依赖关系。对于每个节点,GPT-GNN可以同时计算其属性生成和边生成损失。另外,为了使得GPT-GNN可以处理大图,作者采用了子图采样技术,并提出自适应嵌入队列来缓解负采样带来的不准确损失。
二.预备知识
之前关于图上预训练的工作可以分为两类:
- network/graph embedding:直接参数化节点嵌入向量,并通过保留一些相似度量来参数化的优化节点嵌入。但该种方式学到的嵌入不能用于初始化其他模型,以便对其他任务进行微调。
- transfer learning setting:预训练一个可用于处理不同任务的通用GNN。
三.GNN的生成式预训练
3.1 GNN预训练问题
为什么需要预训练?
获取足够的标注数据通常具有挑战性,尤其是对于大图,这阻碍了通用GNN的训练。为此,有必要探索GNN的预训练,它能用很少的标签进行泛化。
GNN预训练的正式定义:GNN预训练的目标是完全基于单个(大规模)图 G = ( V , E , X ) G=(\mathcal{V}, \mathcal{E}, \mathcal{X}) G=(V,E,X) 学习一个通用的GNN模型 f θ f_\theta fθ,而不需要标注数据,这使得 f θ f_\theta fθ对于同一个图或同一领域的图上的各种下游任务是一个良好的初始化。
3.2 生成式预训练框架
作者提出GPT-GNN,它通过重建/生成输入图的结构或属性来预训练GNN。
给定输入图 G = ( V , E , X ) G=(\mathcal{V}, \mathcal{E}, \mathcal{X}) G=(V,E,X),GNN模型 f θ f_\theta fθ,作者用GNN f θ f_\theta fθ建模图上的似然(likelihood)为 p ( G ; θ ) p(G;\theta) p(G;θ),其表示图 G G G中的节点是如何归属(attributed)和连接(connected)的。GPT-GNN旨在预训练GNN来最大化图似然,即 θ ∗ = max θ p ( G ; θ ) \theta^{*} = \text{max}_{\theta}\ p(G;\theta) θ∗=maxθ p(G;θ)。
3.2.1 如何建模 p ( G ; θ ) p(G;\theta) p(G;θ)
现有的大多数图生成方式采用自回归的方式对概率目标进行因式分解,即按图中的节点顺序来,通过将每个新到达的节点连接到现有节点来生成边。类似地,作者用排列(permutation)向量
π
\pi
π来确定节点顺序,其中
i
π
i^{\pi}
iπ表示排列
π
\pi
π中第
i
i
i个位置的节点id。因此,图分布
p
(
G
,
θ
)
p(G,\theta)
p(G,θ)等价于所有可能排列的期望的可能性,即:
p
(
G
;
θ
)
=
E
π
[
p
θ
(
X
π
,
E
π
)
]
,
p(G ; \theta)=\mathbb{E}_\pi\left[p_\theta\left(X^\pi, E^\pi\right)\right],
p(G;θ)=Eπ[pθ(Xπ,Eπ)],
其中
X
π
∈
R
∣
V
∣
×
d
X^\pi \in \mathbb{R}|\mathcal{V}| \times d
Xπ∈R∣V∣×d表示排列的节点属性,
E
E
E是边集,
E
i
π
E_i^\pi
Eiπ表示与
i
π
i^{\pi}
iπ相连的所有边。为了简化,作者假设观察任何节点排列
π
\pi
π的概率相同。给定一个排列顺序,可以自回归分解log四让,每次迭代生成一个节点:
log
p
θ
(
X
,
E
)
=
∑
i
=
1
∣
V
∣
log
p
θ
(
X
i
,
E
i
∣
X
<
i
,
E
<
i
)
\log p_\theta(X, E)=\sum_{i=1}^{|\mathcal{V}|} \log p_\theta\left(X_i, E_i \mid X_{<i}, E_{<i}\right)
logpθ(X,E)=i=1∑∣V∣logpθ(Xi,Ei∣X<i,E<i)
在每一步
i
i
i,作者使用
i
i
i之前的所有生成的节点,以及其对应的属性
X
<
i
X_{<i}
X<i、节点间的结构
E
<
i
E_{<i}
E<i来生成新的节点
i
i
i,包括
i
i
i的属性
X
i
X_i
Xi和与已有节点的连接
E
i
E_i
Ei。
3.3 分解属性图生成
对于条件概率
p
θ
(
X
i
,
E
i
∣
X
<
i
,
E
<
i
)
p_\theta\left(X_i, E_i \mid X_{<i}, E_{<i}\right)
pθ(Xi,Ei∣X<i,E<i) 的建模,一个简单的解决方案是假设
X
i
X_i
Xi和
E
i
E_i
Ei是独立的,即:
p
θ
(
X
i
,
E
i
∣
X
<
i
,
E
<
i
)
=
p
θ
(
X
i
∣
X
<
i
,
E
<
i
)
⋅
p
θ
(
E
i
∣
X
<
i
,
E
<
i
)
p_\theta\left(X_i, E_i \mid X_{<i}, E_{<i}\right)=p_\theta\left(X_i \mid X_{<i}, E_{<i}\right) \cdot p_\theta\left(E_i \mid X_{<i}, E_{<i}\right)
pθ(Xi,Ei∣X<i,E<i)=pθ(Xi∣X<i,E<i)⋅pθ(Ei∣X<i,E<i)
采用该种方式时,对每个节点其属性和连接之间的依赖关系被完全忽略了,但这种忽略的依赖性确是属性图的核心属性,也是GNN中卷积聚合的基础,因此,这种朴素的分解不能为预训练GNN提供指导。
为了解决这一问题,作者提出了依赖感知(dependency-aware)分解机制来进行属性图的生成。具体来说,在估计一个新节点的属性时,其结构信息会被给定,反之亦然,即属性图的生成可以分为两步:
- 给定观测到的边,生成节点属性;
- 给定观察到的边和生成的节点属性,生成剩余的边。
通过这种方式,模型可以捕获每个节点的属性和结构之间的依赖关系。
令
o
o
o表示
E
i
E_i
Ei中所有观察到的边的索引向量,则
E
i
,
o
E_{i,o}
Ei,o表示观测到的边。
¬
o
\neg o
¬o表示所有掩去边的索引,即待生成的边。基于此,条件概率可以重写为所有观察到的边的期望可能性:
p
θ
(
X
i
,
E
i
∣
X
<
i
,
E
<
i
)
=
∑
o
p
θ
(
X
i
,
E
i
,
¬
o
∣
E
i
,
o
,
X
<
i
,
E
<
i
)
⋅
p
θ
(
E
i
,
o
∣
X
<
i
,
E
<
i
)
=
E
o
[
p
θ
(
X
i
,
E
i
,
¬
o
∣
E
i
,
o
,
X
<
i
,
E
<
i
)
]
=
E
o
[
p
θ
(
X
i
∣
E
i
,
o
,
X
<
i
,
E
<
i
)
⏟
1) generate attributes
⋅
p
θ
(
E
i
,
¬
o
∣
E
i
,
o
,
X
≤
i
,
E
<
i
)
⏟
2) generate edges
]
.
\begin{aligned} & p_\theta\left(X_i, E_i \mid X_{<i}, E_{<i}\right) \\ = & \sum_o p_\theta\left(X_i, E_{i, \neg o} \mid E_{i, o}, X_{<i}, E_{<i}\right) \cdot p_\theta\left(E_{i, o} \mid X_{<i}, E_{<i}\right) \\ = & \mathbb{E}_o\left[p_\theta\left(X_i, E_{i, \neg o} \mid E_{i, o}, X_{<i}, E_{<i}\right)\right] \\ = & \mathbb{E}_o[\underbrace{p_\theta\left(X_i \mid E_{i, o}, X_{<i}, E_{<i}\right)}_{\text {1) generate attributes }} \cdot \underbrace{p_\theta\left(E_{i, \neg o} \mid E_{i, o}, X_{\leq i}, E_{<i}\right)}_{\text {2) generate edges }}] . \end{aligned}
===pθ(Xi,Ei∣X<i,E<i)o∑pθ(Xi,Ei,¬o∣Ei,o,X<i,E<i)⋅pθ(Ei,o∣X<i,E<i)Eo[pθ(Xi,Ei,¬o∣Ei,o,X<i,E<i)]Eo[1) generate attributes
pθ(Xi∣Ei,o,X<i,E<i)⋅2) generate edges
pθ(Ei,¬o∣Ei,o,X≤i,E<i)].
其中
p
θ
(
X
i
∣
E
i
,
o
,
X
<
i
,
E
<
i
)
p_\theta\left(X_i \mid E_{i, o}, X_{<i}, E_{<i}\right)
pθ(Xi∣Ei,o,X<i,E<i)表示节点
i
i
i的属性生成,基于观测到的边
E
i
,
o
E_{i, o}
Ei,o,可以聚集目标节点
i
i
i的邻域信息来生成属性
X
i
X_i
Xi。
p
θ
(
E
i
,
¬
o
∣
E
i
,
o
,
X
≤
i
,
E
<
i
)
p_\theta\left(E_{i, \neg o} \mid E_{i, o}, X_{\leq i}, E_{<i}\right)
pθ(Ei,¬o∣Ei,o,X≤i,E<i)表示生成掩去的边,基于观测到的边
E
i
,
o
E_{i, o}
Ei,o和生成的属性
X
i
X_i
Xi,可以生成目标节点
i
i
i的表示,然后预测
E
i
,
¬
o
E_{i, \neg o}
Ei,¬o内的每条边是否存在。
3.4 高效的属性和边生成
作者希望同时进行属性生成和边生成,但边的生成需要节点属性作为输入,可以泄露给属性生成。为了避免信息泄露,作者将每个节点设计为两种类型:
- Attribute Generation Nodes:作者将这些节点的属性掩去,并使用dummy token代替它们的属性,并学得一个共享的向量 X i n i t X^{init} Xinit来表示它。
- Edge Generation Nodes:对这些节点保持其属性,并将其作为GNN的输入。
作者使用 h A t t r h^{A t t r} hAttr和 h E d g e h^{E d g e} hEdge来分别表示Attribute Generation和Edge Generation节点,由于Attribute Generation Nodes被掩去, h Attr h^{\text {Attr }} hAttr 比 h E d g e h^{E d g e} hEdge包含更少的信息。因此,在进行GNN的消息传递的时候,仅使用Edge Generation Nodes的输出 h E d g e h^{E d g e} hEdge作为对外信息。然后,使用这两组节点的表示来生成具有不同解码器的属性和边。
对于属性生成,将其对应解码器表示为
Dec
A
t
t
r
(
⋅
)
\text{Dec}^{Attr}(\cdot)
DecAttr(⋅),它以
h
Attr
h^{\text {Attr }}
hAttr 作为输入,生成被掩去的属性。建模的选择取决于属性的类型。例如如果一个节点的输入属性是文本,则使用文本生成器模型(例如,LSTM)来生成它。此外,作者定义距离函数来作为生成属性和真实值间的度量,即属性生成损失定义为:
L
i
Attr
=
Distance
(
Dec
Attr
(
h
i
Attr
)
,
X
i
)
.
\mathcal{L}_i^{\text {Attr }}=\text { Distance }\left(\text { Dec }^{\text {Attr }}\left(h_i^{\text {Attr }}\right), X_i\right) .
LiAttr = Distance ( Dec Attr (hiAttr ),Xi).
对于边的生成,作者假设每条边的生成都是独立的,然后可以隐式分解似然:
p
θ
(
E
i
,
¬
o
∣
E
i
,
o
,
X
≤
i
,
E
<
i
)
=
∏
j
+
∈
E
i
,
¬
o
p
θ
(
j
+
∣
E
i
,
o
,
X
≤
i
,
E
<
i
)
.
p_\theta\left(E_{i, \neg o} \mid E_{i, o}, X_{\leq i}, E_{<i}\right)=\prod_{j^{+} \in E_{i, \neg o}} p_\theta\left(j^{+} \mid E_{i, o}, X_{\leq i}, E_{<i}\right) .
pθ(Ei,¬o∣Ei,o,X≤i,E<i)=j+∈Ei,¬o∏pθ(j+∣Ei,o,X≤i,E<i).
在获取到Edge Generation node表示
h
E
d
g
e
h^{E d g e}
hEdge后,可以通过
Dec
E
d
g
e
(
h
i
E
d
g
e
,
h
j
E
d
g
e
)
\operatorname{Dec}^{E d g e}\left(h_i^{E d g e}, h_j^{E d g e}\right)
DecEdge(hiEdge,hjEdge)来建模节点
i
i
i与节点
j
j
j连接的可能性,其中
D
e
c
E
d
g
e
Dec^{E d g e}
DecEdge表示成对(pairwise)得分函数。最后,采用负对比估计(negative contrastive estimation)来计算每个链接节点
j
+
j^{+}
j+的似然。作者将为连接的节点表示为
S
i
−
S_i^{-}
Si−,对比损失计算公式如下:
L
i
E
d
g
e
=
−
∑
j
+
∈
E
i
,
¬
o
log
exp
(
Dec
E
d
g
e
(
h
i
E
d
g
e
,
h
j
+
E
d
g
e
)
)
∑
j
∈
S
i
−
∪
{
j
+
}
exp
(
Dec
E
d
g
e
(
h
i
E
d
g
e
,
h
j
E
d
g
e
)
)
\mathcal{L}_i^{E d g e}=-\sum_{j^{+} \in E_{i, \neg o}} \log \frac{\exp \left(\operatorname{Dec}^{E d g e}\left(h_i^{E d g e}, h_{j^{+}}^{E d g e}\right)\right)}{\sum_{j \in S_i^{-} \cup\left\{j^{+}\right\}} \exp \left(\operatorname{Dec}^{E d g e}\left(h_i^{E d g e}, h_j^{E d g e}\right)\right)}
LiEdge=−j+∈Ei,¬o∑log∑j∈Si−∪{j+}exp(DecEdge(hiEdge,hjEdge))exp(DecEdge(hiEdge,hj+Edge))
下图便展示了属性图生成的过程:
- 确定输入图的节点排列顺序;
- 随机选取目标节点边的一部分作为观测边 E i , o E_{i,o} Ei,o,剩下的边掩去作为 E i , ¬ o E_{i, \neg o} Ei,¬o,需要将被掩去的边从图中删除。
- 将节点划分为Attribute Generation和Edge Generation节点。
- 使用修改的邻接矩阵来计算节点3、4和5的表示,包括它们的Attribute和Edge Generation节点。
- 通过每个节点的属性预测和掩去边预测任务并行训练GNN模型。
3.5 扩展到异配和大图
本节主要介绍如何在大图和异配图上应用GPT-GNN进行预训练。
异配图:对于异配图,所提出的GPT-GNN框架可以直接应用于预训练异构GNN。唯一的区别是每种类型的节点和边都可以有自己的解码器,这是由异构gnn指定的,而不是预训练框架。所有其他组件保持完全相同。
大图:对于大图,则需要使用子图采样进行训练。为了估计GPT-GNN提出的对比损失,需要遍历输入图的所有节点。然而,只能访问子图中的采样节点来估计这个损失,使得(自)监督只关注局部信号。为了缓解这个问题,作者提出了自适应队列(Adaptive Queue),它将之前采样的子图中的节点表示存储为负样本。每次处理一个新的子图,可以通过添加最新的节点表示并删除最旧的节点表示来逐步更新这个队列。自适应队列可以使用更大的负样本池 S i − S_i^{-} Si−,此外,不同采样子图上的节点可以为对比学习带来全局结构指导。