Erin Shellman
Erin Shellman

Reputation: 3713

How to retain vertex names when combining graphs in iGraph?

I'm trying to combine to graphs with graph.union in iGraph, but when I do the resulting graph does not retain its vertex labels.

testGraph1 = barabasi.game(3, 
    m = 5,
    power = 0.6, 
    out.pref = TRUE,
    zero.appeal = 0.5,
    directed = TRUE)
V(testGraph1)$name = c('one', 'two', 'three')   

testGraph2 = barabasi.game(5, 
    m = 5,
    power = 0.6, 
    out.pref = TRUE,
    zero.appeal = 0.5,
    directed = TRUE)    
V(testGraph2)$name = c('one', 'two', 'three', 'four', 'five')   

combine = graph.union(testGraph1, testGraph2)
V(combine)$name #Is NULL

I also tried using graph.union.by.name, but I think there's a bug because both of the test graphs are definitely directed but I'm getting a weird error.

combine = graph.union.by.name(testGraph1, testGraph2)
#Error: !is.directed(g1) & !is.directed(g2) is not TRUE

Upvotes: 2

Views: 2393

Answers (1)

Spacedman
Spacedman

Reputation: 94277

There seems to be a check at the start of graph.union.by.name that doesn't match up with the docs. If you remove that, and also add a directed option to the last line, I think you do get what you want:

gubm = function (g1, g2, dir=FALSE) 
{
  #stopifnot(!is.directed(g1) & !is.directed(g2))
    dv1 = igraph:::get.vertices.as.data.frame(g1)
    dv2 = igraph:::get.vertices.as.data.frame(g2)
    de1 = igraph:::get.edges.as.data.frame(g1)
    de2 = igraph:::get.edges.as.data.frame(g2)
    dv = igraph:::safer.merge(dv1, dv2, all = TRUE)
    de = igraph:::safer.merge(de1, de2, all = TRUE)
    g = igraph:::graph.data.frame(de, directed = dir, vertices = dv)
    return(g)
}

> combine=gubm(testGraph1,testGraph2,TRUE)
> V(combine)$name
[1] "one"   "three" "two"   "five"  "four" 

But check this on plenty of examples to make sure it behaves properly. I suspect the igraph developers will spot this here, but you should report it as a bug on the igraph mailing list or in the igraph bug tracker.

I think the reason graph.union doesn't preserve the names is because there's no guarantee that all the graphs in the call will have the same attributes on their nodes, and its too much bother to check...

Upvotes: 2

Related Questions