Search code examples
rggplot2network-programming

plot a network based on given values


I have a data frame like this:

df <- data.frame(char1=c('a', 'd', 'i', 'k', 'm', 'd', 'e', 'e', 'q', 'i','q', 'm','n','i'), 
    char2=c('b','a','a','g','n','b', 'o', 'g', 'p', 'b','g','b','k','d'),
 value=c(0.8,0.6,0.6,0.5,0.5,0.4,0.3,0.2,0.1,0.1,0.4,-0.1,-0.2,-0.3))

I want to plot a network in which each character is a node and the value between each node and another is represented by a link. The higher the value, the closer the link. And the nodes that have high values with each other, such as node 'a', 'b', and 'd' can have a cluster plot showing their strong relations.


Solution

  • Here's a start, based on this question (I exponentiated the weight values given because I think the weights have to be positive: you could modify this if you wanted)

    library(igraph)
    g <- graph_from_data_frame(df)
    L <- layout_with_fr(g, weights = exp(df$value))
    plot(g, layout = L)
    

    network graph showing i, a, b, d in a tight cluster

    It's not clear what your other options are for negative weights; as far as I can see there aren't any igraph layout options that allow for negative weights; most of those algorithms assume that the attractive force between nodes is proportional to the strength of their (positive) weights. Negative weights could in principle allow for repulsion, but I don't think that's implemented. Speaking subjectively, I don't see the problem with exponentiating; nodes connected by negative weights are still farther apart than those connected by positive weights (since exponentiation maps negative weights to values between 0 and 1).