1 -- Profile_simple.Play --
2 package main
3
4 import (
5 "fmt"
6 "log"
7 "sort"
8
9 "golang.org/x/exp/rand"
10
11 "gonum.org/v1/gonum/graph/community"
12 "gonum.org/v1/gonum/graph/internal/ordered"
13 "gonum.org/v1/gonum/graph/simple"
14 )
15
16 func main() {
17 // Profile calls Modularize which implements the Louvain modularization algorithm.
18 // Since this is a randomized algorithm we use a defined random source to ensure
19 // consistency between test runs. In practice, results will not differ greatly
20 // between runs with different PRNG seeds.
21 src := rand.NewSource(1)
22
23 // Create dumbell graph:
24 //
25 // 0 4
26 // |\ /|
27 // | 2 - 3 |
28 // |/ \|
29 // 1 5
30 //
31 g := simple.NewUndirectedGraph()
32 for u, e := range smallDumbell {
33 for v := range e {
34 g.SetEdge(simple.Edge{F: simple.Node(u), T: simple.Node(v)})
35 }
36 }
37
38 // Get the profile of internal node weight for resolutions
39 // between 0.1 and 10 using logarithmic bisection.
40 p, err := community.Profile(
41 community.ModularScore(g, community.Weight, 10, src),
42 true, 1e-3, 0.1, 10,
43 )
44 if err != nil {
45 log.Fatal(err)
46 }
47
48 // Print out each step with communities ordered.
49 for _, d := range p {
50 comm := d.Communities()
51 for _, c := range comm {
52 sort.Sort(ordered.ByID(c))
53 }
54 sort.Sort(ordered.BySliceIDs(comm))
55 fmt.Printf("Low:%.2v High:%.2v Score:%v Communities:%v Q=%.3v\n",
56 d.Low, d.High, d.Score, comm, community.Q(g, comm, d.Low))
57 }
58
59 }
60
61 // intset is an integer set.
62 type intset map[int]struct{}
63
64 func linksTo(i ...int) intset {
65 if len(i) == 0 {
66 return nil
67 }
68 s := make(intset)
69 for _, v := range i {
70 s[v] = struct{}{}
71 }
72 return s
73 }
74
75 var smallDumbell = []intset{
76 0: linksTo(1, 2),
77 1: linksTo(2),
78 2: linksTo(3),
79 3: linksTo(4, 5),
80 4: linksTo(5),
81 5: nil,
82 }
83
84 -- Profile_simple.Output --
85 Low:0.1 High:0.29 Score:14 Communities:[[0 1 2 3 4 5]] Q=0.9
86 Low:0.29 High:2.3 Score:12 Communities:[[0 1 2] [3 4 5]] Q=0.714
87 Low:2.3 High:3.5 Score:4 Communities:[[0 1] [2] [3] [4 5]] Q=-0.31
88 Low:3.5 High:10 Score:0 Communities:[[0] [1] [2] [3] [4] [5]] Q=-0.607
89
90 -- Profile_multiplex.Play --
91
92 package main
93
94 import (
95 "fmt"
96 "log"
97 "sort"
98
99 "golang.org/x/exp/rand"
100
101 "gonum.org/v1/gonum/graph/community"
102 "gonum.org/v1/gonum/graph/internal/ordered"
103 "gonum.org/v1/gonum/graph/simple"
104 )
105
106 var friends, enemies *simple.WeightedUndirectedGraph
107
108 func main() {
109 // Profile calls ModularizeMultiplex which implements the Louvain modularization
110 // algorithm. Since this is a randomized algorithm we use a defined random source
111 // to ensure consistency between test runs. In practice, results will not differ
112 // greatly between runs with different PRNG seeds.
113 src := rand.NewSource(1)
114
115 // The undirected graphs, friends and enemies, are the political relationships
116 // in the Middle East as described in the Slate article:
117 // http://www.slate.com/blogs/the_world_/2014/07/17/the_middle_east_friendship_chart.html
118 g, err := community.NewUndirectedLayers(friends, enemies)
119 if err != nil {
120 log.Fatal(err)
121 }
122 weights := []float64{1, -1}
123
124 // Get the profile of internal node weight for resolutions
125 // between 0.1 and 10 using logarithmic bisection.
126 p, err := community.Profile(
127 community.ModularMultiplexScore(g, weights, true, community.WeightMultiplex, 10, src),
128 true, 1e-3, 0.1, 10,
129 )
130 if err != nil {
131 log.Fatal(err)
132 }
133
134 // Print out each step with communities ordered.
135 for _, d := range p {
136 comm := d.Communities()
137 for _, c := range comm {
138 sort.Sort(ordered.ByID(c))
139 }
140 sort.Sort(ordered.BySliceIDs(comm))
141 fmt.Printf("Low:%.2v High:%.2v Score:%v Communities:%v Q=%.3v\n",
142 d.Low, d.High, d.Score, comm, community.QMultiplex(g, comm, weights, []float64{d.Low}))
143 }
144
145 }
146 -- Profile_multiplex.Output --
147 Low:0.1 High:0.72 Score:26 Communities:[[0] [1 7 9 12] [2 8 11] [3 4 5 10] [6]] Q=[24.7 1.97]
148 Low:0.72 High:1.1 Score:24 Communities:[[0 6] [1 7 9 12] [2 8 11] [3 4 5 10]] Q=[16.9 14.1]
149 Low:1.1 High:1.2 Score:18 Communities:[[0 2 6 11] [1 7 9 12] [3 4 5 8 10]] Q=[9.16 25.1]
150 Low:1.2 High:1.6 Score:10 Communities:[[0 3 4 5 6 10] [1 7 9 12] [2 8 11]] Q=[10.5 26.7]
151 Low:1.6 High:1.6 Score:8 Communities:[[0 1 6 7 9 12] [2 8 11] [3 4 5 10]] Q=[5.56 39.8]
152 Low:1.6 High:1.8 Score:2 Communities:[[0 2 3 4 5 6 10] [1 7 8 9 11 12]] Q=[-1.82 48.6]
153 Low:1.8 High:2.3 Score:-6 Communities:[[0 2 3 4 5 6 8 10 11] [1 7 9 12]] Q=[-5 57.5]
154 Low:2.3 High:2.4 Score:-10 Communities:[[0 1 2 6 7 8 9 11 12] [3 4 5 10]] Q=[-11.2 79]
155 Low:2.4 High:4.3 Score:-52 Communities:[[0 1 2 3 4 5 6 7 8 9 10 11 12]] Q=[-46.1 117]
156 Low:4.3 High:10 Score:-54 Communities:[[0 1 2 3 4 6 7 8 9 10 11 12] [5]] Q=[-82 254]
157
View as plain text