import networkx as nx
import matplotlib.pyplot as plt
# Generate graph
N = 10
G = nx.scale_free_graph(N, seed=0)
G = nx.Graph(G)
#================================================
# nx.enumerate_all_cliques(G):
# 그냥, 존재하는 모든 clique를 리턴함.
# generator를 리턴하는데, list(nx.enumerate_all_cliques(G))로 생각없이 변환할 경우 메모리 터질 수 있음.
print("== nx.enumerate_all_cliques(G)")
clique_num = 0
for clique in nx.enumerate_all_cliques(G):
# clique type: list
clique_num+=1
print(f"all cliques count: {clique_num}")
print("=="*30)
#================================================
# nx.enumerate_all_cliques(G):
# maximal_clique, 각 clique를 포함해서 만들 수 있는 쵀대 크기의 clique를 리턴
print("== nx.find_cliques(G), maximal_clqiues")
for maximal_clique in nx.find_cliques(G):
if len(maximal_clique)>=2:# 크기가 2개짜리(즉 그냥 edge)도 clique이므로 이 아이들은 출력하지 않음.
print(maximal_clique)
print("=="*30)
#================================================
print("== nx.make_clique_bipartite(G)")
# networkx.algorithms.clique.make_clique_bipartite(G)
# node attr: 'bipartite'가 1인 아이들은 node를 말하고, 0인 아이들은 clique를 말함.
# 즉, 0인 가상의 동일한 노드에 연결된 아이들은 모두 서로 clique라는 것을 말함.
# nx.find_cliques(G)와 의미적으로 동일함.
CliqueBiG = nx.make_clique_bipartite(G)
for n, n_attr in CliqueBiG.nodes(data=True):
if n_attr['bipartite']==0:
# clique를 의미하는 가상의 노드
# bipartite가 0인 노드들의 이웃 노드들은 각각 clique가 됨.
print(f"clique_{abs(n):2d} :: {list(CliqueBiG[n])}")
print("==" * 30)
#================================================
# networkx.algorithms.clique.make_max_clique_graph
# clique를 기본 노드로 하는 graph를 새롭게 만들어냄
print("== nx.make_max_clique_graph(G)")
# 의미적으로는 다음과 같음.
def custom_cliqueG(inputG):
# node -- clique bipartitie graph
CliqBiG = nx.make_clique_bipartite(inputG)
# clique를 의미하는 node set
clique_node_set = [n for n, n_attr in CliqBiG.nodes(data=True) if n_attr['bipartite']==0]
# clique만 날리도록 projection
CliqG = nx.bipartite.project(CliqBiG, clique_node_set)
# clique남 남김
return CliqG
assert nx.is_isomorphic(custom_cliqueG(G), nx.make_max_clique_graph(G))
print("Assertion complete")
print("==" * 30)
#================================================
# networkx.algorithms.clique.graph_clique_number
# graph의 clique number는 해당 graph에 존재하는 가장 큰 clique의 크기.
print(f"== nx.graph_clique_number(G): {nx.graph_clique_number(G)}")
def custom_graph_clique_number(G):
max_graph_clique_number = 0
for maximal_clique in nx.find_cliques(G):
l = len(maximal_clique)
if max_graph_clique_number <= l:
max_graph_clique_number=l
return max_graph_clique_number
assert custom_graph_clique_number(G)==nx.graph_clique_number(G)
print("Assertion complete")
print("==" * 30)
#================================================
# networkx.algorithms.clique.graph_number_of_cliques
# graph에서 maximal clique의 크기를 리턴하는 함수
print(f"== nx.graph_number_of_cliques(G): {nx.graph_number_of_cliques(G)}")
def custom_graph_number_of_clique(G):
max_graph_clique_number = 0
for maximal_clique in nx.find_cliques(G):
max_graph_clique_number+=1
return max_graph_clique_number
assert custom_graph_number_of_clique(G) == nx.graph_number_of_cliques(G)
print("Assertion complete")
print("==" * 30)
== nx.enumerate_all_cliques(G)
all cliques count: 32
============================================================
== nx.find_cliques(G), maximal_clqiues
[1, 8]
[1, 2, 0, 5]
[1, 2, 3]
[1, 2, 6]
[4, 2]
[9, 7]
[7, 5]
[7, 6]
============================================================
== nx.make_clique_bipartite(G)
clique_ 1 :: [1, 8]
clique_ 2 :: [1, 2, 0, 5]
clique_ 3 :: [1, 2, 3]
clique_ 4 :: [1, 2, 6]
clique_ 5 :: [4, 2]
clique_ 6 :: [9, 7]
clique_ 7 :: [7, 5]
clique_ 8 :: [7, 6]
============================================================
== nx.make_max_clique_graph(G)
Assertion complete
============================================================
== nx.graph_clique_number(G): 4
Assertion complete
============================================================
== nx.graph_number_of_cliques(G): 8
Assertion complete
============================================================
댓글남기기