-
Notifications
You must be signed in to change notification settings - Fork 185
Conversation
What do you mean by "indices of the edges"? We don't have edge indices in LG. |
Based on the code, it looks like edge indices means the pair of vertices
|
Codecov Report
@@ Coverage Diff @@
## master #1105 +/- ##
==========================================
+ Coverage 93.86% 93.87% +<.01%
==========================================
Files 90 91 +1
Lines 4354 4375 +21
==========================================
+ Hits 4087 4107 +20
- Misses 267 268 +1 |
Ok, I've replaced One more question: if I use the |
It should be good to go/review on my side: the reduction in test coverage seems to be an artefact as the untested line is between two lines that are tested. |
src/biconnectivity/bridge.jl
Outdated
""" | ||
bridge(g) | ||
Compute the [bridges](https://en.m.wikipedia.org/wiki/Bridge_(graph_theory)) | ||
of a connected graph `g` and return an array containing all bridges. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
As this can be done in a single sentence, I think we should describe here what a bridge is.
src/biconnectivity/bridge.jl
Outdated
Edge 1 => 2 | ||
``` | ||
""" | ||
function bridge(g::AbstractGraph) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I would call this bridges
instead.
g
should be restricted to undirected graphs, unless we can define what the bridge of a directed graph is.
Also, we should restrict g
to integer eltypes here, as the function will not work otherwise.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
bridge
is a bit ambiguous for directed graphs, better to restrict the dispatch.
Concerning the name, I agree bridges
makes more sense. I wanted to be consistent with articulation
(which should maybe be articulations
instead?), but maybe it's better to call this bridges
and deprecate articulation
to articulations
in the future.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think articulation
is shorthand for articulation_points
. But I agree that this should be bridges
.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I see, yes this should definitely be bridges
.
I'm a bit unsure what's the correct dispatch, because it is not clear to me that all graphs types defined in various packages are subtypes of SimpleGraphs.AbstractSimpleGraph
. Maybe easier to accept all AbstractGraph{<:Integer}
and throw an argument error if the graph is directed.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
We use the package SimpleTraits.jl
for dispatching on directed/undirected graphs. For an example on how to do that, you can have a look at the file LightGraphs/src/community/cliques.jl
. The function maximal_cliques
is restricted to undirected graphs there.
I wouldn't bother with vertices that are not integers if there is not a simple and performant way to do such a thing. As far as I know, there is no package that uses such a graph yet and if there was, that person would have to implement many other functions from LightGraphs anyway, as they will not work out of the box.
src/biconnectivity/bridge.jl
Outdated
|
||
function Bridges(g::AbstractGraph) | ||
n = nv(g) | ||
T = typeof(n) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
You can use eltype(g)
here.
src/biconnectivity/bridge.jl
Outdated
state.depth[v] = state.id | ||
state.low[v] = state.depth[v] | ||
|
||
for w in outneighbors(g, v) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Maybe put an @inbounds
in front of to the loop.
This recursive algorithm is great, but in the future we might have to replace it with a iterative one, as this code already gives me a stack overflow: Don't worry about coverage, that is broken at the moment. |
I see, if the depth first search graph is very deep things just fail... Ideally we could have a DFS iterator that one would use to code this algorithms? Maybe even a "Tarjan" iterator. |
Well, we've played with that in the past but the problem is that calling generic visiting / opening / closing functions makes things horribly slow so we specialze the DFS for each algorithm that needs it. See Edited to add: we've made a conscious decision in the past to remove functions that don't scale to large graphs. I don't see us adding any functions that can't handle, say, 1 million nodes / 100 million edges without crashing. |
I think that code was slow because of pre v0.6 implementation stuff. I think you could write a generic visitor code now and it wouldn't be slower. The old way was to pass the hooks in as arguments. But I think the new Julia 1.0 way is to define a prehook(t::VisitorType, g, v)
onhook(t::VisitorType, g, v)
posthook(t::VisitorType, g, v) |
@jpfairbanks I'd be really interested in bringing back the traversal code if we can show that it's as fast. I'll open up an issue and maybe one of the GSOC candidates can use it to get familiar w/ our codebase. |
Should have implemented most of the feedback. I'm really curious about the |
I think this could be merged. @abhinavmehndiratta is working on an iterative version of the similar |
add newlines between signature and start of doc
* implement bridge computation * added tests * fix reference * fix docstring * change to Edge * simplify test * fix tests * fix tests for real * just add one edge * remove unnecessary lines * implement suggestions * rename to bridges * added check for undirectedness * use dispatch on trait IsDirected * update docs * Update bridge.jl add newlines between signature and start of doc
This implements a function to compute all bridges of a graph. My main doubt is what should be the output format of this (returning a subset of edges). I have opted for an array of
CartesianIndex
with the indices of the edges (which is what one generally gets when doingfindall
on a matrix), but maybe simply a list ofTuple
or a tuple of arrays would make more sense.I also plan to implement "edge-biconnected components" but I think that can be done in a separate PR.