feat: add `as.vector` parameter to `as_edgelist()`
Users need edge lists in the flat vector format c(from1, to1, from2, to2, ...) for make_graph() and C library interop. Currently requires inefficient transpose workaround: as.vector(t(as_edgelist(g))).
Changes
- Added
as.vectorparameter toas_edgelist()(defaults toFALSEfor backward compatibility) - When
TRUE, returns flat vector directly from C layer without matrix conversion - Works with both numeric IDs and vertex names
- ~38% faster than transpose workaround
Usage
g <- make_graph(c(1, 2, 2, 3, 3, 4, 4, 5))
# Before: inefficient transpose
edges <- as.vector(t(as_edgelist(g, names = FALSE)))
# After: direct vector output
edges <- as_edgelist(g, names = FALSE, as.vector = TRUE)
# Suitable for make_graph()
g2 <- make_graph(edges)
Addresses use cases in leidenbase (#39) and leidenAlg (#13) for efficient graph conversion.
Original prompt
This section details on the original issue you should resolve
<issue_title>Obtain an edges vector in a form suitable for make_graph()</issue_title> <issue_description>What is the feature or improvement you would like to see?
There should be a function that retrieves an edge list in a form suitable for
make_graph(), as well as suitable for the C functionigraph_create().
as_edgelist()returns a matrix, not a vector, and converting to a vector gives the vertex IDs in the wrong order:> g<-make_graph(c(1,2, 2,3, 3,4, 4,5)) > as.vector(as_edgelist(g, names=F)) [1] 1 2 3 4 2 3 4 5Instead one must transpose the matrix first, which is inefficient:
> as.vector(t(as_edgelist(g, names=F))) [1] 1 2 2 3 3 4 4 5A more efficient way is
> .Call(igraph:::R_igraph_get_edgelist, g, F) [1] 0 1 1 2 2 3 3 4but this uses an internal function.
Use cases for the feature
For libraries that need to convert igraph graphs efficiently, such as leidenbase or leidenalg.
References
- https://github.com/cole-trapnell-lab/leidenbase/issues/39
- https://github.com/kharchenkolab/leidenAlg/issues/13 </issue_description>
Comments on the Issue (you are @copilot in this section)
@schochastics This is `as_edgelist` ```r as_edgelist res }Simple solution would be to a add a bool (just `arg` here) that defaults to `TRUE`? ```r as_edgelist <- function(graph, names = TRUE, arg = TRUE) { ensure_igraph(graph) on.exit(.Call(R_igraph_finalizer)) res <- matrix(.Call(R_igraph_get_edgelist, graph, TRUE), ncol = 2) res <- res + 1 if(arg){ res <- matrix(.Call(R_igraph_get_edgelist, graph, TRUE), ncol = 2) if (names && "name" %in% vertex_attr_names(graph)) { res <- matrix(V(graph)$name[res], ncol = 2) } } else{ res <- .Call(R_igraph_get_edgelist, graph, FALSE) if (names && "name" %in% vertex_attr_names(graph)) { res <- V(graph)$name[res] } } res } ```</body></comment_new> </comments>
- Fixes igraph/rigraph#864
💬 We'd love your input! Share your thoughts on Copilot coding agent in our 2 minute survey.