令
G
(
V
,
E
,
L
V
,
L
E
,
φ
)
G(V,E,L_V,L_E,\varphi)
G(V,E,LV,LE,φ)表示一个带标签的图,其中
V
V
V和
E
E
E分别表示顶点集和边集,
L
V
L_V
LV和
L
E
L_E
LE分别表示顶点和边的标签集,
φ
\varphi
φ是一个标签函数定义了
V
→
L
V
V \to L_V
V→LV和
E
→
L
E
E \to L_E
E→LE的映射。
FSM算法根据操作的数据不同,可以分为针对图数据库的和针对一个大图的(现在只讨论exact match方法)。
根据每个顶点标签的id对顶点进行排序,然后根据该顺序生成邻接矩阵
X
k
X_k
Xk,
k
k
k表示顶点个数。邻接矩阵中每个元素表示该边标签的id。
对于
X
k
=
(
x
1
,
1
x
1
,
2
x
1
,
3
⋯
x
1
,
k
x
2
,
1
x
2
,
2
x
2
,
3
⋯
x
2
,
k
x
3
,
1
x
3
,
2
x
3
,
3
⋯
x
3
,
k
⋮
⋮
⋮
⋱
⋮
x
k
,
1
x
k
,
2
x
k
,
3
⋯
x
k
,
k
)
X_k=\begin{pmatrix} x_{1,1} & x_{1,2} & x_{1,3} &\cdots &x_{1,k}\\ x_{2,1} & x_{2,2} & x_{2,3} & \cdots &x_{2,k}\\ x_{3,1} & x_{3,2} & x_{3,3} & \cdots &x_{3,k}\\ \vdots & \vdots & \vdots &\ddots &\vdots \\ x_{k,1} & x_{k,2} & x_{k,3} & \cdots &x_{k,k}\\ \end{pmatrix}
Xk=⎝⎜⎜⎜⎜⎜⎛x1,1x2,1x3,1⋮xk,1x1,2x2,2x3,2⋮xk,2x1,3x2,3x3,3⋮xk,3⋯⋯⋯⋱⋯x1,kx2,kx3,k⋮xk,k⎠⎟⎟⎟⎟⎟⎞
如果是无向图,则
c
o
d
e
(
X
k
)
=
x
1
,
1
x
1
,
2
x
2
,
2
x
1
,
3
x
2
,
3
x
3
,
3
x
1
,
4
⋯
x
k
−
1
,
k
x
k
,
k
code(X_k)=x_{1,1}x_{1,2}x_{2,2}x_{1,3}x_{2,3}x_{3,3}x_{1,4}\cdots x_{k-1,k}x_{k,k}
code(Xk)=x1,1x1,2x2,2x1,3x2,3x3,3x1,4⋯xk−1,kxk,k
如果是有向图,则
c
o
d
e
(
X
k
)
=
x
1
,
1
x
1
,
2
x
2
,
1
x
2
,
2
x
1
,
3
x
3
,
1
x
2
,
3
x
3
,
2
⋯
x
k
−
1
,
k
x
k
,
k
−
1
x
k
,
k
code(X_k)=x_{1,1}x_{1,2}x_{2,1}x_{2,2}x_{1,3}x_{3,1}x_{2,3}x_{3,2}\cdots x_{k-1,k}x_{k,k-1}x_{k,k}
code(Xk)=x1,1x1,2x2,1x2,2x1,3x3,1x2,3x3,2⋯xk−1,kxk,k−1xk,k。
对于一个子图
G
s
G_s
Gs,定义它的支持度
s
u
p
(
G
s
)
sup(G_s)
sup(Gs)为数据库中包含该子图的图的个数与总数的比值。
如果两个邻接矩阵
X
k
X_k
Xk,
Y
k
Y_k
Yk除了第
k
k
k行和第
k
k
k列不同外,其余元素均相同,则将两个矩阵合并生成
Z
k
+
1
Z_{k+1}
Zk+1。如下所示:
X
k
=
(
X
k
−
1
x
1
x
2
T
x
k
k
)
X_k = \begin{pmatrix} X_{k-1} & \boldsymbol {x_1}\\ \boldsymbol {x^T_2} & x_{kk}\\ \end{pmatrix}
Xk=(Xk−1x2Tx1xkk),
Y
k
=
(
Y
k
−
1
y
1
y
2
T
y
k
k
)
Y_k = \begin{pmatrix} Y_{k-1} & \boldsymbol {y_1}\\ \boldsymbol {y^T_2} & y_{kk}\\ \end{pmatrix}
Yk=(Yk−1y2Ty1ykk)
Z
k
+
1
=
(
X
k
−
1
x
1
y
1
x
2
T
x
k
k
z
k
,
k
+
1
y
2
T
z
k
+
1
,
k
y
k
k
)
Z_{k+1} = \begin{pmatrix} X_{k-1} & \boldsymbol {x_1} & \boldsymbol {y_1}\\ \boldsymbol {x^T_2} & x_{kk}& z_{k,k+1}\\ \boldsymbol {y^T_2} &z_{k+1,k}& y_{kk}\\ \end{pmatrix}
Zk+1=⎝⎛Xk−1x2Ty2Tx1xkkzk+1,ky1zk,k+1ykk⎠⎞,也可写成
其中,新矩阵中的元素满足下列关系:
如果是无向图,那么
z
k
+
1
,
k
z_{k+1,k}
zk+1,k和
z
k
,
k
+
1
z_{k,k+1}
zk,k+1相同。该合并操作可以产生多个
Z
k
+
1
Z_{k+1}
Zk+1矩阵,这是因为
v
k
v_k
vk和
v
k
+
1
v_{k+1}
vk+1的构成的边的label可以有多种选择,因为图数据库中不同的图中这两个点之间的边的不同,也就造成了该边的label的不同,因此
z
k
+
1
,
k
z_{k+1,k}
zk+1,k和
z
k
,
k
+
1
z_{k,k+1}
zk,k+1有多个选择,还有一种选择是没有边,既0。
当
X
k
X_k
Xk和
Y
k
Y_k
Yk中的
v
k
v_k
vk的label相同时,交换
X
k
X_k
Xk和
Y
k
Y_k
Yk后生成的矩阵是一样的,为了避免这种情况,只有当
c
o
d
e
(
t
h
e
f
i
r
s
t
m
a
t
r
i
x
)
<
=
c
o
d
e
(
t
h
e
s
e
c
o
n
d
m
a
t
r
i
x
)
code(the\ first\ matrix)<=code(the\ second\ matrix)
code(the first matrix)<=code(the second matrix)时才生成矩阵,生成的矩阵也被称为normal form。只有当大小为
k
+
1
k+1
k+1的图
G
G
G的所有
k
k
k子图都是频繁子图时,
G
G
G才是频繁子图候选项。
如果通过删除一个节点得到的子图不是normal form,必须将其转换成normal form之后才能判断该子图是否已经生成过。通过以下步骤,可以将一个non-normal form 的矩阵
X
k
X_k
Xk转换成normal form的矩阵
X
k
′
X'_k
Xk′:(1)对
X
k
X_k
Xk中的每个节点生成一个
1
×
1
1 \times 1
1×1的邻接矩阵;(2)对于点
v
i
,
v
j
∈
G
(
X
k
)
v_i,v_j \in G(X_k)
vi,vj∈G(Xk),如果其邻接矩阵符合合并条件,则合并;(3)不断地合并新生成的矩阵,知道获得了一个
k
×
k
k \times k
k×k的矩阵
X
k
′
X'_k
Xk′。该过程涉及到的是行列式的操作,因此可以表示成
X
k
′
=
(
T
k
)
T
X
k
T
k
X'_k=(T_k)^T X_k T_k
Xk′=(Tk)TXkTk。
当所有候选子图生成后,需要统计每个子图的支持度。但是每个图的normal form并不是唯一的。因此需要将代表同一个子图的不同的normal form的支持度加在一起。为了索引代表同一个子图的不同normal form,定义了normal form的canonical form。定义
G
G
G的canonical form是
G
G
G的normal form中
c
o
d
e
code
code最小的。令
X
k
−
1
m
X^m_{k-1}
Xk−1m表示
G
(
X
k
)
G(X_k)
G(Xk)移除点
v
m
v_m
vm后得到的图。
X
k
−
1
′
m
X^{'m}_{k-1}
Xk−1′m表示
X
k
−
1
m
X^m_{k-1}
Xk−1m经过
T
k
−
1
m
T^m_{k-1}
Tk−1m变换后得到的normal form。
X
k
−
1
′
m
X^{'m}_{k-1}
Xk−1′m经过
S
k
−
1
m
S^m_{k-1}
Sk−1m变换后得到canonical form。整体过程可表示为
(
T
k
−
1
m
S
k
−
1
m
)
T
X
k
−
1
m
T
k
−
1
m
S
k
−
1
m
(T^m_{k-1}S^m_{k-1})^TX^m_{k-1}T^m_{k-1}S^m_{k-1}
(Tk−1mSk−1m)TXk−1mTk−1mSk−1m。
那么我们可以用
S
k
m
S^m_k
Skm和
T
k
m
T^m_k
Tkm将
X
k
X_k
Xk转换成canonical form
X
c
k
X_{ck}
Xck。而
S
k
m
S^m_k
Skm和
T
k
m
T^m_k
Tkm又可以通过
S
k
−
1
m
S^m_{k-1}
Sk−1m和
T
k
−
1
m
T^m_{k-1}
Tk−1m获得。具体过程如下所示:
寻找频繁子图时,对数据库中的每个图从1到k的构造子图,并计算每个子图的支持度。