graph/community: add threshold for modularity gain
MODIFY
graph/community/louvain_common.go
graph/community/louvain_common.go
@@ -356,6 +356,9 @@ func (s *slice) TakeMin(p *int) bool {
const (
negativeWeight = "community: unexpected negative edge weight"
positiveWeight = "community: unexpected positive edge weight"
+
+ // deltaQtol is the tolerance for progression of the local moving heuristic's improvement of Q.
+ deltaQtol = 1e-15
)
// positiveWeightFuncFor returns a constructed weight function for the

MODIFY
graph/community/louvain_directed.go
graph/community/louvain_directed.go
@@ -544,7 +544,7 @@ func (l *directedLocalMover) localMovingHeuristic(rnd func(int) int) (done bool)
l.shuffle(rnd)
for _, n := range l.nodes {
dQ, dst, src := l.deltaQ(n)
- if dQ <= 0 {
+ if dQ <= deltaQtol {
continue
}
l.move(dst, src)

MODIFY
graph/community/louvain_directed_multiplex.go
graph/community/louvain_directed_multiplex.go
@@ -747,7 +747,7 @@ func (l *directedMultiplexLocalMover) localMovingHeuristic(rnd func(int) int) (d
l.shuffle(rnd)
for _, n := range l.nodes {
dQ, dst, src := l.deltaQ(n)
- if dQ <= 0 {
+ if dQ <= deltaQtol {
continue
}
l.move(dst, src)

MODIFY
graph/community/louvain_undirected.go
graph/community/louvain_undirected.go
@@ -486,7 +486,7 @@ func (l *undirectedLocalMover) localMovingHeuristic(rnd func(int) int) (done boo
l.shuffle(rnd)
for _, n := range l.nodes {
dQ, dst, src := l.deltaQ(n)
- if dQ <= 0 {
+ if dQ <= deltaQtol {
continue
}
l.move(dst, src)

MODIFY
graph/community/louvain_undirected_multiplex.go
graph/community/louvain_undirected_multiplex.go
@@ -686,7 +686,7 @@ func (l *undirectedMultiplexLocalMover) localMovingHeuristic(rnd func(int) int)
l.shuffle(rnd)
for _, n := range l.nodes {
dQ, dst, src := l.deltaQ(n)
- if dQ <= 0 {
+ if dQ <= deltaQtol {
continue
}
l.move(dst, src)

graph/community: add threshold for modularity gain