Closed pelegm closed 4 years ago
Branch: u/pelegm/cheeger
Branch pushed to git repo; I updated commit sha1. New commits:
0cb6192 | Implementing edge isoperimetric number (#21942) |
Will rebase to develop
.
@videlec, perhaps we can work on this together on some notebook on the cloud or somewhere else?
I know nothing about those functions. However, two general notes:
One-sentence descriptions will be used in the toc and they should really be just one sentence. It is kind of dull to have "Return the edge-isoperimetric number of a graph." when the name is edge_isoperimetric_number()
, but there is no good alternative. (When there is no real one-line description like for example size()
has.)
Please test for empty graphs. See #21741 for bugs we already have had.
Thanks for the feedback. I am currently testing a better algorithm, based on gray codes. I will also modify the docstrings appropriately, and test/fix the method for empty graphs (and, in general, for graphs with no edges).
There is no consensus about the definition of Cheeger constants for the empty graph and the graph with 1 vertex. I suggest that we will raise an exception if the graph is empty, and return infinity if the graph contains a single vertex (so that usual lower bounds on the mixing time of the random walk on the graph will not fail).
The Cheeger constant of a disconnected graph is 0. I should add that as a heuristic at the beginning of each of the methods.
You could do the following to reduce overall computation time:
for k in range(1, self.order()//2):
for s in Subsets(self.vertices(), k):
....
and of course start methods testing the trivial cases.
I strongly believe that the best way to go is a C backtracker implemented on sparse C graphs. It will be at least 100x faster. With the current code it is not even possible to make computation with graphs with 20 vertices.
You could do the following to reduce overall computation time:
Well, this will not do for the Cheeger constant, but might help the isoperimetric numbers.
I strongly believe that the best way to go is a C backtracker implemented on sparse C graphs. It will be at least 100x faster. With the current code it is not even possible to make computation with graphs with 20 vertices.
You are right: it is very slow. However, I must say that I have no idea how to implement stuff in C. About the backtracker you've offered: do you think that we should simply use a gray code which traverses the entire lattice, or should we really think of something smarter that traverses (mostly) only the relevant subsets? This is probably just a matter of a X2 speed factor, I believe (probably even much less).
Let me try it now.
Branch pushed to git repo; I updated commit sha1. This was a forced push. New commits:
1988a75 | Cheeger constant (#21942) |
6214e44 | Implementing edge isoperimetric number (#21942) |
94f8a45 | Fixing some documentation bugs #21942 |
f07babf | Vertex isoperimetric number #21942 |
4f86191 | Check the cases empty graph and single vertex WIP |
In the meanwhile, I have rebased to 7.5beta4 and added some heuristics.
Branch pushed to git repo; I updated commit sha1. New commits:
a06c7de | Better docstrings & aliases, references moved |
I am considering changing the doc index from Algorithmically hard stuff to Expansion properties. What do you think?
Replying to @pelegm:
I am considering changing the doc index from Algorithmically hard stuff to Expansion properties. What do you think?
Whole idea of Algorithmically hard stuff as a TOC headear is odd. To compare, posets have Properties of the poset, even when height
is trivial, width
is harder but polynomial and dimension
is proven to not be in P
.
So yes, please do that.
I push a C implementation at u/vdelecroix/cheeger
which seems to coincide with the one here ;-)
sage: from sage.graphs.isoperimetric_inequalities import cheeger
sage: G = graphs.CubeGraph(4)
sage: %time G.cheeger_constant()
CPU times: user 4.12 s, sys: 52 ms, total: 4.18 s
Wall time: 4.1 s
1/4
sage: %time cheeger(G)
CPU times: user 0 ns, sys: 0 ns, total: 0 ns
Wall time: 1.97 ms
1/4
but not all ;-(
sage: G = graphs.FibonacciTree(6)
sage: %time G.cheeger_constant()
CPU times: user 1min 3s, sys: 28 ms, total: 1min 3s
Wall time: 1min 3s
1/15
sage: %time cheeger(G)
CPU times: user 16 ms, sys: 0 ns, total: 16 ms
Wall time: 14.5 ms
1/13
I can not work on it right now. I will debug later.
I will verify my algorithm for the Fibonacci tree, and if it looks fine I will have a look at your code. Thanks!
I believe that mine is wrong. Anyway it is worth to look at the code. In particular are there situations were we can perform cheap branch cut?
Well, I guess that at least for trees the algorithm can be vastly improved.
This paper: http://ac.els-cdn.com/0095895689900294/1-s2.0-0095895689900294-main.pdf?_tid=c92aa55e-b880-11e6-a64e-00000aab0f02&acdnat=1480677575_44a9c4d6e1d9a6be9b2770c5d14f7ecf claims there is a linear algorithm for calculating the edge isoperimetric number of trees. It is a corollary of a more general statement, according to which for every connected graph there exists a partition of its vertex set to X and Y such that the subgraphs induced by these sets are both connected and the (edge) isoperimetric number equals |E(X,Y)|/min{|X|,|Y|}.
Indeed, if we can restrict to connected X and Y in the parition then it is much better! I was not expecting something that strong. However I do not see linearity coming in. There are many partitions X,Y of the vertices so that both induced graphs are connected.
The algorithm works in general and is linear on trees!
The algorithm now also finds Cheeger constant (and not only edge isoperimetric number) of trees.
1) You should test the case with 1 vertex.
2) I fixed the backtracker in C. It is still available at u/vdelecroix/cheeger
. It would be easy to adapt to the other constants.
Changed branch from u/pelegm/cheeger to u/vdelecroix/21942
TODO:
Branch pushed to git repo; I updated commit sha1. This was a forced push. New commits:
8e9f2ee | C backtracker for Cheeger constant |
Branch pushed to git repo; I updated commit sha1. This was a forced push. New commits:
8484a37 | 21942: Cheeger constant |
Changed keywords from cheeger, isoperimetric, random walk, days79 to cheeger, MathExp2018
Changed author from Peleg Michaeli to Vincent Delecroix
Description changed:
---
+++
@@ -1,7 +1,7 @@
-I have implemented an algorithm to find the so-called Cheeger constant of a graph. There are various definitions for this constant, I have chosen one which is sometimes also called **transition isoperimetric number**.
+This ticket adds three methods to graphs to compute three variations of the Cheeger constant:
-It would be nice to add an alias method `self.transition_isoperimetric_number`, but I am not sure what is the right way of doing this.
-
-I plan to add an implementation for other isoperimetric numbers, such as the **edge isoperimetric number** (sometimes simply called **isoperimetric number**) and the **vertex isoperimetric number** (sometimes called the **magnifying constant**).
+- the "transition isoperimetric number" (`cheeger_constant`)
+- the edge isoperimetric number (`edge_isoperimetric_number`)
+- the vertex isoperimetric number or magnifying constant (`vertex_isoperimetric_number`)
Note that the implemented Cheeger constant is also the **conductance** of the simple random walk on the graph.
Thanks for all your work on this!
The code looks fine, testing a couple of cases on my machine works great, however, I cannot build the docs, but it seems like the issue is not with your new code (I get [graphs ] OSError: [graphs ] /media/peleg/peleg/sage/local/lib/python2.7/site-packages/sage/combinat/designs/incidence_structures.py:docstring of sage.combinat.designs.incidence_structures.IncidenceStructure.is_generalized_quadrangle:3: WARNING: citation not found: BH12
).
Would you call it a positive review?
Replying to @pelegm:
The code looks fine, testing a couple of cases on my machine works great, however, I cannot build the docs, but it seems like the issue is not with your new code (I get
[graphs ] OSError: [graphs ] /media/peleg/peleg/sage/local/lib/python2.7/site-packages/sage/combinat/designs/incidence_structures.py:docstring of sage.combinat.designs.incidence_structures.IncidenceStructure.is_generalized_quadrangle:3: WARNING: citation not found: BH12
).
It might be something on your computer. It looks fine with the patchbot as well as on my computer. Did you do a make doc-clean
before building the doc?
This is how it looks like:
peleg@etti:develop:~/sage$ git fetch trac u/vdelecroix/21942
From git://trac.sagemath.org/sage
* branch u/vdelecroix/21942 -> FETCH_HEAD
peleg@etti:develop:~/sage$ git checkout -b 21942 FETCH_HEAD
Switched to a new branch '21942'
peleg@etti:21942:~/sage$ make doc-clean
...
Sage build/upgrade complete!
peleg@etti:21942:~/sage$ sage --docbuild reference/graphs html
...
[graphs ] /media/peleg/peleg/sage/local/lib/python2.7/site-packages/sage/combinat/designs/incidence_structures.py:docstring of sage.combinat.designs.incidence_structures.IncidenceStructure.is_generalized_quadrangle:3: WARNING: citation not found: BH12
...
[graphs ] WARNING: Error building the documentation.
[graphs ] Traceback (most recent call last):
[graphs ] File "/media/peleg/peleg/sage/local/lib/python2.7/runpy.py", line 174, in _run_module_as_main
[graphs ] "__main__", fname, loader, pkg_name)
[graphs ] File "/media/peleg/peleg/sage/local/lib/python2.7/runpy.py", line 72, in _run_code
[graphs ] exec code in run_globals
[graphs ] File "/media/peleg/peleg/sage/local/lib/python2.7/site-packages/sage_setup/docbuild/__main__.py", line 2, in <module>
[graphs ] main()
[graphs ] File "/media/peleg/peleg/sage/local/lib/python2.7/site-packages/sage_setup/docbuild/__init__.py", line 1713, in main
[graphs ] builder()
[graphs ] File "/media/peleg/peleg/sage/local/lib/python2.7/site-packages/sage_setup/docbuild/__init__.py", line 749, in _wrapper
[graphs ] getattr(DocBuilder, build_type)(self, *args, **kwds)
[graphs ] File "/media/peleg/peleg/sage/local/lib/python2.7/site-packages/sage_setup/docbuild/__init__.py", line 130, in f
[graphs ] runsphinx()
[graphs ] File "/media/peleg/peleg/sage/local/lib/python2.7/site-packages/sage_setup/docbuild/sphinxbuild.py", line 276, in runsphinx
[graphs ] sys.stderr.raise_errors()
[graphs ] File "/media/peleg/peleg/sage/local/lib/python2.7/site-packages/sage_setup/docbuild/sphinxbuild.py", line 216, in raise_errors
[graphs ] raise OSError(self._error)
[graphs ] OSError: [graphs ] /media/peleg/peleg/sage/local/lib/python2.7/site-packages/sage/combinat/designs/incidence_structures.py:docstring of sage.combinat.designs.incidence_structures.IncidenceStructure.is_generalized_quadrangle:3: WARNING: citation not found: BH12
This ticket adds three methods to graphs to compute three variations of the Cheeger constant:
cheeger_constant
)edge_isoperimetric_number
)vertex_isoperimetric_number
)Note that the implemented Cheeger constant is also the conductance of the simple random walk on the graph.
CC: @videlec @JeremiasE @slel
Component: graph theory
Keywords: cheeger, MathExp2018
Author: Vincent Delecroix, David Coudert
Branch:
8389196
Reviewer: Peleg Michaeli, Frédéric Chapoton
Issue created by migration from https://trac.sagemath.org/ticket/21942