圖作為一種數(shù)據(jù)結(jié)構(gòu),由節(jié)點(diǎn)和邊組成,可由下圖表示。其中一個(gè)邊只能鏈接兩個(gè)節(jié)點(diǎn)。一個(gè)圖可表示為G=(v,e,w)
其中v表示節(jié)點(diǎn),e表示邊,w表示節(jié)點(diǎn)的特征。關(guān)于圖的表示可參考,本文不再詳述。
對(duì)于超圖,其與圖結(jié)構(gòu)最主要的區(qū)別就是一條邊可以連接多個(gè)節(jié)點(diǎn),因此我們可以認(rèn)為圖是一種特殊的超圖。超圖結(jié)構(gòu)如下圖所示。
超圖可表示為G=(υ,ε,ω)。其中υ為節(jié)點(diǎn)集合,ε為超邊集合,ω為超邊權(quán)重的對(duì)稱矩陣。超圖G可以關(guān)聯(lián)矩陣H來(lái)表示,其詞條定義為:
改公式可解釋為如果某個(gè)節(jié)點(diǎn)屬于某個(gè)超邊,則關(guān)聯(lián)矩陣H的值為1,否則為0。
對(duì)于單個(gè)節(jié)點(diǎn)v可定義為:
可解釋為連接該節(jié)點(diǎn)的所有邊乘上權(quán)重向量的和。
Dₑ和Dᵥ由d(v)和s(e)分別表示為超邊和節(jié)點(diǎn)的對(duì)角矩陣。
單個(gè)邊可定義為:
可以理解為該邊包含的所有節(jié)點(diǎn)之和。
下面舉出一個(gè)具體實(shí)例幫助理解超圖的構(gòu)建。以該圖為例
圖中有8個(gè)節(jié)點(diǎn),3個(gè)超邊。超邊的細(xì)化圖如下:
假設(shè)權(quán)重W為全1矩陣,因?yàn)樗鼘?duì)構(gòu)建超圖數(shù)據(jù)結(jié)果無(wú)影響,那么H為一個(gè)3行8列的矩陣,表示為:
h(1,1) = 0
h(2,1) = 1
h(3,1) = 0
h(4,1) = 1
h(5,1) = 0
h(6,1) = 0
h(7,1) = 0
h(8,1) = 1
h(1,2) = 1
h(2,2) = 0
h(3,2) = 0
h(4,2) = 0
h(5,2) = 0
h(6,2) = 1
h(7,2) = 1
h(8,2) = 0
h(1,3) = 0
h(2,3) = 0
h(3,3) = 1
h(4,3) = 0
h(5,3) = 1
h(6,3) = 0
h(7,3) = 1
h(8,3) = 0
De表示為:
d(1) = 1
d(2) = 1
d(3) = 1
d(4) = 1
d(5) = 1
d(6) = 1
d(7) = 2
d(8) = 1
Dv表示為:
s(1) = 3
s(2) = 3
s(3) = 3
下面我們用python代碼進(jìn)行編程,我們的目標(biāo)是在知道節(jié)點(diǎn)的特征W通過(guò)特征的距離來(lái)生成 G \mathcal{G} G矩陣。路線為:W,H, G \mathcal{G} G。主要代碼如下:
import numpy as np #KNN生成H x = np.array([[1,0,0,0,1,0,1,0,0,0], [1,1,1,0,0,0,1,1,1,0], [1,1,1,0,0,1,1,1,1,0], [0,1,0,0,0,0,1,0,1,0], [1,1,1,1,0,0,1,1,0,1], [1,0,1,0,0,1,0,1,1,0], [0,1,0,0,1,0,1,1,1,0], [0,1,1,0,1,0,1,0,1,1]]) def Eu_dis(x): """ Calculate the distance among each raw of x :param x: N X D N: the object number D: Dimension of the feature :return: N X N distance matrix """ x = np.mat(x) aa = np.sum(np.multiply(x, x), 1) ab = x * x.T dist_mat = aa + aa.T - 2 * ab dist_mat[dist_mat 0] = 0 dist_mat = np.sqrt(dist_mat) dist_mat = np.maximum(dist_mat, dist_mat.T) return dist_mat def hyperedge_concat(*H_list): """ Concatenate hyperedge group in H_list :param H_list: Hyperedge groups which contain two or more hypergraph incidence matrix :return: Fused hypergraph incidence matrix """ H = None for h in H_list: if h is not None and h != []: # for the first H appended to fused hypergraph incidence matrix if H is None: H = h else: if type(h) != list: H = np.hstack((H, h)) else: tmp = [] for a, b in zip(H, h): tmp.append(np.hstack((a, b))) H = tmp return H def construct_H_with_KNN_from_distance(dis_mat, k_neig, is_probH=True, m_prob=1): """ construct hypregraph incidence matrix from hypergraph node distance matrix :param dis_mat: node distance matrix :param k_neig: K nearest neighbor :param is_probH: prob Vertex-Edge matrix or binary :param m_prob: prob :return: N_object X N_hyperedge """ n_obj = dis_mat.shape[0] # construct hyperedge from the central feature space of each node n_edge = n_obj H = np.zeros((n_obj, n_edge)) for center_idx in range(n_obj): dis_mat[center_idx, center_idx] = 0 dis_vec = dis_mat[center_idx] nearest_idx = np.array(np.argsort(dis_vec)).squeeze() avg_dis = np.average(dis_vec) if not np.any(nearest_idx[:k_neig] == center_idx): nearest_idx[k_neig - 1] = center_idx for node_idx in nearest_idx[:k_neig]: if is_probH: H[node_idx, center_idx] = np.exp(-dis_vec[0, node_idx] ** 2 / (m_prob * avg_dis) ** 2) else: H[node_idx, center_idx] = 1.0 return H def construct_H_with_KNN(X, K_neigs=[10], split_diff_scale=False, is_probH=True, m_prob=1): """ init multi-scale hypergraph Vertex-Edge matrix from original node feature matrix :param X: N_object x feature_number :param K_neigs: the number of neighbor expansion :param split_diff_scale: whether split hyperedge group at different neighbor scale :param is_probH: prob Vertex-Edge matrix or binary :param m_prob: prob :return: N_object x N_hyperedge """ if len(X.shape) != 2: X = X.reshape(-1, X.shape[-1]) if type(K_neigs) == int: K_neigs = [K_neigs] dis_mat = Eu_dis(X) H = [] for k_neig in K_neigs: H_tmp = construct_H_with_KNN_from_distance(dis_mat, k_neig, is_probH, m_prob) if not split_diff_scale: H = hyperedge_concat(H, H_tmp) else: H.append(H_tmp) return H H = construct_H_with_KNN(x) #生成G def generate_G_from_H(H, variable_weight=False): """ calculate G from hypgraph incidence matrix H :param H: hypergraph incidence matrix H :param variable_weight: whether the weight of hyperedge is variable :return: G """ if type(H) != list: return _generate_G_from_H(H, variable_weight) else: G = [] for sub_H in H: G.append(generate_G_from_H(sub_H, variable_weight)) return G def _generate_G_from_H(H, variable_weight=False): """ calculate G from hypgraph incidence matrix H :param H: hypergraph incidence matrix H :param variable_weight: whether the weight of hyperedge is variable :return: G """ H = np.array(H) n_edge = H.shape[1] # the weight of the hyperedge W = np.ones(n_edge) # the degree of the node DV = np.sum(H * W, axis=1) # the degree of the hyperedge DE = np.sum(H, axis=0) invDE = np.mat(np.diag(np.power(DE, -1))) DV2 = np.mat(np.diag(np.power(DV, -0.5))) W = np.mat(np.diag(W)) H = np.mat(H) HT = H.T if variable_weight: DV2_H = DV2 * H invDE_HT_DV2 = invDE * HT * DV2 return DV2_H, W, invDE_HT_DV2 else: G = DV2 * H * W * invDE * HT * DV2 return G G = generate_G_from_H(H)
實(shí)驗(yàn)結(jié)果:
H
G
到此這篇關(guān)于如何建立一個(gè)超圖的文章就介紹到這了,希望對(duì)你有幫助,更多相關(guān)超圖內(nèi)容請(qǐng)搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章,希望大家以后多多支持腳本之家!
標(biāo)簽:股票 駐馬店 中山 畢節(jié) 湖州 衡水 江蘇 呼和浩特
巨人網(wǎng)絡(luò)通訊聲明:本文標(biāo)題《如何建立一個(gè)超圖詳解》,本文關(guān)鍵詞 如何,建立,一個(gè),超圖,詳解,;如發(fā)現(xiàn)本文內(nèi)容存在版權(quán)問(wèn)題,煩請(qǐng)?zhí)峁┫嚓P(guān)信息告之我們,我們將及時(shí)溝通與處理。本站內(nèi)容系統(tǒng)采集于網(wǎng)絡(luò),涉及言論、版權(quán)與本站無(wú)關(guān)。