Network Analysis in R

Ted Laderas (laderast@ohsu.edu)

October 24, 2017

Overview

Network Data Representations useful in R

The igraph package

What you need to run these slides

I used the following libraries to generate these slides.

require(igraph)
require(knitr)
require(visNetwork)
require(shiny)

Loading in Data into igraph

The igraph package has parsers for reading in most of the general file formats for networks. Let’s load in the Karate network from Network Example Data. It’s in GML format, so we’ll need to specify that when we use read_graph().

library(igraph)
karate <- read_graph("data/karate.gml", format="gml")
class(karate)
## [1] "igraph"
plot.igraph(karate)

Adding Labels and Improving the Layout

That’s not very informative, especially since the original data doesn’t have labels. Let’s add some:

get.vertex.attribute(karate, "id")
##  [1]  1  2  3  4  5  6  7  8  9 10 11 12 13 14 15 16 17 18 19 20 21 22 23
## [24] 24 25 26 27 28 29 30 31 32 33 34
karate <- set.vertex.attribute(karate, "name", 
                               value=c("Chloe", "Emily", "Aaliyah", "Emma", 
                                       "Jennifer", "Olivia", "Hannah",
                                       "Jessica", "Sarah", "Lily", "Charlotte", 
                                       "Elizabeth", "Abigail", "Rebecca",
                                       "Samantha", "Jacob", "Muhammad", "Shawn", 
                                        "Aaron", "Daniel", "Jonah", "Alex", 
                                       "Michael", "James", "Ryan", "Jordan", 
                                       "Alexander", "Ali", "Tyler", "Kevin", 
                                       "Jack", "Ethan", "Luke", "Harry"))

#V() is a way to programmatically access vertices (or nodes) for igraph
V(karate)
## + 34/34 vertices, named:
##  [1] Chloe     Emily     Aaliyah   Emma      Jennifer  Olivia    Hannah   
##  [8] Jessica   Sarah     Lily      Charlotte Elizabeth Abigail   Rebecca  
## [15] Samantha  Jacob     Muhammad  Shawn     Aaron     Daniel    Jonah    
## [22] Alex      Michael   James     Ryan      Jordan    Alexander Ali      
## [29] Tyler     Kevin     Jack      Ethan     Luke      Harry
#get the ids (as a vector)
V(karate)$name
##  [1] "Chloe"     "Emily"     "Aaliyah"   "Emma"      "Jennifer" 
##  [6] "Olivia"    "Hannah"    "Jessica"   "Sarah"     "Lily"     
## [11] "Charlotte" "Elizabeth" "Abigail"   "Rebecca"   "Samantha" 
## [16] "Jacob"     "Muhammad"  "Shawn"     "Aaron"     "Daniel"   
## [21] "Jonah"     "Alex"      "Michael"   "James"     "Ryan"     
## [26] "Jordan"    "Alexander" "Ali"       "Tyler"     "Kevin"    
## [31] "Jack"      "Ethan"     "Luke"      "Harry"
#look at edges
E(karate)
## + 78/78 edges (vertex names):
##  [1] Chloe   --Emily     Chloe   --Aaliyah   Emily   --Aaliyah  
##  [4] Chloe   --Emma      Emily   --Emma      Aaliyah --Emma     
##  [7] Chloe   --Jennifer  Chloe   --Olivia    Chloe   --Hannah   
## [10] Jennifer--Hannah    Olivia  --Hannah    Chloe   --Jessica  
## [13] Emily   --Jessica   Aaliyah --Jessica   Emma    --Jessica  
## [16] Chloe   --Sarah     Aaliyah --Sarah     Aaliyah --Lily     
## [19] Chloe   --Charlotte Jennifer--Charlotte Olivia  --Charlotte
## [22] Chloe   --Elizabeth Chloe   --Abigail   Emma    --Abigail  
## [25] Chloe   --Rebecca   Emily   --Rebecca   Aaliyah --Rebecca  
## [28] Emma    --Rebecca   Olivia  --Muhammad  Hannah  --Muhammad 
## + ... omitted several edges

A More informative plot

#layout example from https://rulesofreason.wordpress.com/2012/11/05/network-visualization-in-r-with-the-igraph-package/
plot.igraph(karate, layout=layout.fruchterman.reingold, # the layout method. see the igraph documentation for details
        main='Karate Friends!', #specifies the title
        #vertex.label.dist=0.5,         #puts the name labels slightly off the dots
        vertex.label.color='black',     #the color of the name labels
        vertex.label.font=1,            #the font of the name labels
        vertex.label=V(karate)$name,        #specifies the labels of the vertices. in this case the 'name' attribute is used
        vertex.label.cex=0.75,          #specifies the size of the font of the labels. can also be made to vary
        vertex.size=degree(karate)*1.5, #make node size proportional to number of connections
        edge.arrow.size=2
)

Graph Attributes

Each element of a graph (vertices and edges) can be customized by passing in the appropriate attribute. For more info, check out http://www.inside-r.org/packages/cran/igraph/docs/attributes.

Some properties are automatically mapped, such as V(graph)$color or E(graph)$color. If you add a new attribute, you’ll need to map this to a plotting property in plot.igraph()

Remember, that after changing graph properties, such as node size, you need to run your layout_ function again.

#setting node properties
#can also use set.vertex.attributes() here
newKarate <- karate

faction <- c(1, 1, 1, 1, 1, 1, 1, 1, 2, 2, 1, 1, 1, 1, 2, 2, 1, 1, 2, 
                     1, 2, 1, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2)
V(newKarate)$color <- faction

#Set edge attributes using E(accessor)
#can pass a named list for each node as well
#You can also use set.edge.attributes() here
E(newKarate)$color <- "red"

#Here we instantiate a weight vector using sample
weightvec <- sample(c(1,2,3,4), length(E(newKarate)), replace = TRUE)
#Name each edge
names(weightvec) <- E(newKarate)$name
weightvec
##  [1] 2 3 2 3 2 4 1 3 3 1 3 4 2 2 1 3 4 3 1 1 1 3 3 2 2 2 3 3 1 1 4 3 1 1 4
## [36] 4 2 1 1 1 1 3 1 4 3 1 4 4 4 4 1 4 2 4 4 3 4 1 2 2 1 4 2 4 2 3 3 3 2 3
## [71] 2 4 3 3 3 1 2 3
E(newKarate)$weight <- weightvec

#note we need to map an attribute to a property of the graph (igraph is dumb)
plot(newKarate, edge.width=E(karate)$weight)

Simple Measures

Degree Distribution and Average Path Length

degree(karate)
##     Chloe     Emily   Aaliyah      Emma  Jennifer    Olivia    Hannah 
##        16         9        10         6         3         4         4 
##   Jessica     Sarah      Lily Charlotte Elizabeth   Abigail   Rebecca 
##         4         5         2         3         1         2         5 
##  Samantha     Jacob  Muhammad     Shawn     Aaron    Daniel     Jonah 
##         2         2         2         2         2         3         2 
##      Alex   Michael     James      Ryan    Jordan Alexander       Ali 
##         2         2         5         3         3         2         4 
##     Tyler     Kevin      Jack     Ethan      Luke     Harry 
##         3         4         4         6        12        17
sort(degree(karate), decreasing = TRUE)
##     Harry     Chloe      Luke   Aaliyah     Emily      Emma     Ethan 
##        17        16        12        10         9         6         6 
##     Sarah   Rebecca     James    Olivia    Hannah   Jessica       Ali 
##         5         5         5         4         4         4         4 
##     Kevin      Jack  Jennifer Charlotte    Daniel      Ryan    Jordan 
##         4         4         3         3         3         3         3 
##     Tyler      Lily   Abigail  Samantha     Jacob  Muhammad     Shawn 
##         3         2         2         2         2         2         2 
##     Aaron     Jonah      Alex   Michael Alexander Elizabeth 
##         2         2         2         2         2         1
hist(degree(karate))

average.path.length(karate)
## [1] 2.4082
shortPaths <- get.shortest.paths(karate, from="Muhammad")

plot(karate, mark.groups=shortPaths$vpath[c(10)])

Drunken Stumbling

Let’s generate a random walk from Jennifer and see where we get.

w <- random_walk(karate, start = "Jennifer", steps =1000)

#who is the most visited?
sort(table(w$name), decreasing = TRUE)
## 
##     Chloe     Harry      Luke   Aaliyah     Emily     Ethan    Olivia 
##       120       102        65        52        47        42        35 
##    Jordan   Rebecca      Emma    Hannah     James Charlotte   Jessica 
##        33        33        31        31        31        28        28 
##     Sarah  Jennifer      Ryan       Ali    Daniel      Jack     Jacob 
##        28        25        25        23        23        21        21 
##     Tyler     Kevin     Jonah   Abigail  Muhammad     Aaron      Lily 
##        19        17        15        14        14        13        12 
##      Alex Elizabeth   Michael  Samantha Alexander     Shawn 
##        11        11        10         8         6         6
#normalize table by number of visits
probKarate <- table(w$name)/1000

Influencers

Who are the influencers (or hubs) in this social network? Let’s use some network centrality measures to see. Are there any differences?

Who gives the highest correlation with our drunken walk probabilities?

pr <- page.rank(karate)
sort(pr$vector, decreasing = TRUE)
##       Harry       Chloe        Luke     Aaliyah       Emily       Ethan 
## 0.100919182 0.096997285 0.071693226 0.057078509 0.052876924 0.037158087 
##        Emma       James       Sarah     Rebecca      Olivia      Hannah 
## 0.035859858 0.031522515 0.029766056 0.029536456 0.029111155 0.029111155 
##       Kevin         Ali        Jack     Jessica    Jennifer   Charlotte 
## 0.026288538 0.025639767 0.024590155 0.024490497 0.021977952 0.021977952 
##        Ryan      Jordan      Daniel       Tyler    Muhammad   Alexander 
## 0.021076034 0.021006197 0.019604636 0.019573459 0.016784005 0.015044038 
##     Abigail       Shawn        Alex    Samantha       Jacob       Aaron 
## 0.014644892 0.014558677 0.014558677 0.014535994 0.014535994 0.014535994 
##       Jonah     Michael        Lily   Elizabeth 
## 0.014535994 0.014535994 0.014309397 0.009564745
nk <- V(karate)$name
cor(pr$vector[nk], probKarate[nk])
## [1] 0.9684656
ec <- eigen_centrality(karate)
sort(ec$vector, decreasing = TRUE)
##      Harry      Chloe    Aaliyah       Luke      Emily      Sarah 
## 1.00000000 0.95213237 0.84955420 0.82665886 0.71233514 0.60906844 
##    Rebecca       Emma      Ethan       Jack    Jessica      James 
## 0.60657439 0.56561431 0.51165649 0.46806481 0.45789093 0.40207086 
##     Daniel      Kevin        Ali      Tyler       Lily      Jacob 
## 0.39616224 0.36147301 0.35749923 0.35107297 0.27499812 0.27159396 
##   Samantha      Jonah      Aaron    Michael      Shawn       Alex 
## 0.27159396 0.27159396 0.27159396 0.27159396 0.24747879 0.24747879 
##    Abigail     Hannah     Olivia  Charlotte   Jennifer  Alexander 
## 0.22566382 0.21288383 0.21288383 0.20347148 0.20347148 0.20242852 
##     Jordan       Ryan  Elizabeth   Muhammad 
## 0.15857597 0.15280670 0.14156633 0.06330461
cor(ec$vector[nk], probKarate[nk])
## [1] 0.8240622
hs <- hub_score(karate)
sort(hs$vector, decreasing = TRUE)
##      Harry      Chloe    Aaliyah       Luke      Emily      Sarah 
## 1.00000000 0.95213237 0.84955420 0.82665886 0.71233514 0.60906844 
##    Rebecca       Emma      Ethan       Jack    Jessica      James 
## 0.60657439 0.56561431 0.51165649 0.46806481 0.45789093 0.40207086 
##     Daniel      Kevin        Ali      Tyler       Lily   Samantha 
## 0.39616224 0.36147301 0.35749923 0.35107297 0.27499812 0.27159396 
##      Jacob      Aaron      Jonah    Michael      Shawn       Alex 
## 0.27159396 0.27159396 0.27159396 0.27159396 0.24747879 0.24747879 
##    Abigail     Olivia     Hannah   Jennifer  Charlotte  Alexander 
## 0.22566382 0.21288383 0.21288383 0.20347148 0.20347148 0.20242852 
##     Jordan       Ryan  Elizabeth   Muhammad 
## 0.15857597 0.15280670 0.14156633 0.06330461
cor(hs$vector[nk], probKarate[nk])
## [1] 0.8240622

Cliques?

Who’s the most connected groups to each other? Enquiring minds want to know…

##get all cliques in the data
karateCliques <- cliques(karate)
length(karateCliques)
## [1] 170
#let's try finding the largest cliques
largeKarateCliques <- largest_cliques(karate)
largeKarateCliques
## [[1]]
## + 5/34 vertices, named:
## [1] Jessica Chloe   Emily   Aaliyah Emma   
## 
## [[2]]
## + 5/34 vertices, named:
## [1] Emma    Chloe   Emily   Aaliyah Rebecca

What are the Karate communities?

Can we split the network up into smaller communities? There are number of community detection algorithms we can use to see if we can cleanly separate our network into smaller modules, or communities.

##Segment the karate network using the fast-greedy algorithm
fgComm <- fastgreedy.community(karate)
plot(fgComm, karate)

##Segment the karate network using the walktrap algorithm
wkComm <- walktrap.community(karate)
plot(wkComm, karate)

##how close are the algorithms?
compare(membership(fgComm), membership(wkComm))
## [1] 1.14204

Extracting subgraphs from community membership

If there is a community of interest, we can use induced.subgraph.

##extract the membership vector for the fastgreedy community
fgCommMembers <- membership(fgComm)

##let's extract the one of the cliques
clique1 <- induced.subgraph(karate, v=largeKarateCliques[[1]]$name)
plot(clique1)

#how many different communities are there?
levels(factor(fgCommMembers))
## [1] "1" "2" "3"
comm1 <- induced.subgraph(karate, fgCommMembers == 1)
plot(comm1)

Other searches

How do we find all of Emma’s friends?

emmasNeighbors <- neighbors(karate, v="Emma", mode="all")
emmaSubnet <- c("Emma",emmasNeighbors$name)
emmaSubnet
## [1] "Emma"    "Chloe"   "Emily"   "Aaliyah" "Jessica" "Abigail" "Rebecca"
emmaSubgraph <- induced.subgraph(karate, emmaSubnet)
plot(emmaSubgraph)

Other Plot Layouts

igraph’s built in plotting is not super customizable, but you can change layouts. All of the different igraph layouts begin with “layout_”.

#circle plot
plot(karate, layout=layout_in_circle)

#layout plot on grid
plot(karate, layout=layout_on_grid)

#force-directed layout for large graphs
plot(karate, layout=layout_with_lgl)

#layout plot with center (star layout)
plot(karate, layout=layout_as_star)

#layout plot on grid
plot(karate, layout=layout_with_dh)

Generating graphs from scratch

Oftentimes, you will need to generate a bunch of graphs from scratch, for a background distribution. There are some built in functions to do that.

#Random Graphs

rgGraph <- random.graph.game(34, p.or.m = 0.2)
plot(rgGraph)

hist(degree(rgGraph))

#Erdos Renyi Graphs
erGraph <- erdos.renyi.game(34, 0.1)
plot(erGraph)

hist(degree(erGraph))

#Barabasi graphs - power law distributed
bgGraph <- barabasi.game(34, 1)
plot(bgGraph)

#Confirm edge distribution is correct
hist(degree(bgGraph))

Converting igraph Objects to Other Representations

The graph package (not the igraph package!) contains the graphNEL and graphAM representations. I don’t really go into using them here, but just know that you can convert back and forth from these different representations using different commands.

library(graph)
## Loading required package: BiocGenerics
## Loading required package: parallel
## 
## Attaching package: 'BiocGenerics'
## The following objects are masked from 'package:parallel':
## 
##     clusterApply, clusterApplyLB, clusterCall, clusterEvalQ,
##     clusterExport, clusterMap, parApply, parCapply, parLapply,
##     parLapplyLB, parRapply, parSapply, parSapplyLB
## The following objects are masked from 'package:igraph':
## 
##     normalize, union
## The following object is masked from 'package:gridExtra':
## 
##     combine
## The following objects are masked from 'package:stats':
## 
##     IQR, mad, xtabs
## The following objects are masked from 'package:base':
## 
##     anyDuplicated, append, as.data.frame, cbind, colnames,
##     do.call, duplicated, eval, evalq, Filter, Find, get, grep,
##     grepl, intersect, is.unsorted, lapply, lengths, Map, mapply,
##     match, mget, order, paste, pmax, pmax.int, pmin, pmin.int,
##     Position, rank, rbind, Reduce, rownames, sapply, setdiff,
##     sort, table, tapply, union, unique, unsplit, which, which.max,
##     which.min
## 
## Attaching package: 'graph'
## The following objects are masked from 'package:igraph':
## 
##     degree, edges, intersection
#graphNEL objects
karateGN <- igraph.to.graphNEL(karate)
karateGN
## A graphNEL graph with undirected edges
## Number of Nodes = 34 
## Number of Edges = 78
#Adjacency matrix
karateAM <- as(karateGN, "graphAM")
karateAM
## A graphAM graph with undirected edges
## Number of Nodes = 34 
## Number of Edges = 78
#look at the actual adjacency matrix
karateAdjMat <- karateAM@adjMat
rownames(karateAdjMat) <- colnames(karateAdjMat)
rowSums(karateAdjMat)
##     Chloe     Emily   Aaliyah      Emma  Jennifer    Olivia    Hannah 
##        16         9        10         6         3         4         4 
##   Jessica     Sarah      Lily Charlotte Elizabeth   Abigail   Rebecca 
##         4         5         2         3         1         2         5 
##  Samantha     Jacob  Muhammad     Shawn     Aaron    Daniel     Jonah 
##         2         2         2         2         2         3         2 
##      Alex   Michael     James      Ryan    Jordan Alexander       Ali 
##         2         2         5         3         3         2         4 
##     Tyler     Kevin      Jack     Ethan      Luke     Harry 
##         3         4         4         6        12        17
colSums(karateAdjMat)
##     Chloe     Emily   Aaliyah      Emma  Jennifer    Olivia    Hannah 
##        16         9        10         6         3         4         4 
##   Jessica     Sarah      Lily Charlotte Elizabeth   Abigail   Rebecca 
##         4         5         2         3         1         2         5 
##  Samantha     Jacob  Muhammad     Shawn     Aaron    Daniel     Jonah 
##         2         2         2         2         2         3         2 
##      Alex   Michael     James      Ryan    Jordan Alexander       Ali 
##         2         2         5         3         3         2         4 
##     Tyler     Kevin      Jack     Ethan      Luke     Harry 
##         3         4         4         6        12        17
karateAdjMat
##           Chloe Emily Aaliyah Emma Jennifer Olivia Hannah Jessica Sarah
## Chloe         0     1       1    1        1      1      1       1     1
## Emily         1     0       1    1        0      0      0       1     0
## Aaliyah       1     1       0    1        0      0      0       1     1
## Emma          1     1       1    0        0      0      0       1     0
## Jennifer      1     0       0    0        0      0      1       0     0
## Olivia        1     0       0    0        0      0      1       0     0
## Hannah        1     0       0    0        1      1      0       0     0
## Jessica       1     1       1    1        0      0      0       0     0
## Sarah         1     0       1    0        0      0      0       0     0
## Lily          0     0       1    0        0      0      0       0     0
## Charlotte     1     0       0    0        1      1      0       0     0
## Elizabeth     1     0       0    0        0      0      0       0     0
## Abigail       1     0       0    1        0      0      0       0     0
## Rebecca       1     1       1    1        0      0      0       0     0
## Samantha      0     0       0    0        0      0      0       0     0
## Jacob         0     0       0    0        0      0      0       0     0
## Muhammad      0     0       0    0        0      1      1       0     0
## Shawn         1     1       0    0        0      0      0       0     0
## Aaron         0     0       0    0        0      0      0       0     0
## Daniel        1     1       0    0        0      0      0       0     0
## Jonah         0     0       0    0        0      0      0       0     0
## Alex          1     1       0    0        0      0      0       0     0
## Michael       0     0       0    0        0      0      0       0     0
## James         0     0       0    0        0      0      0       0     0
## Ryan          0     0       0    0        0      0      0       0     0
## Jordan        0     0       0    0        0      0      0       0     0
## Alexander     0     0       0    0        0      0      0       0     0
## Ali           0     0       1    0        0      0      0       0     0
## Tyler         0     0       1    0        0      0      0       0     0
## Kevin         0     0       0    0        0      0      0       0     0
## Jack          0     1       0    0        0      0      0       0     1
## Ethan         1     0       0    0        0      0      0       0     0
## Luke          0     0       1    0        0      0      0       0     1
## Harry         0     0       0    0        0      0      0       0     1
##           Lily Charlotte Elizabeth Abigail Rebecca Samantha Jacob Muhammad
## Chloe        0         1         1       1       1        0     0        0
## Emily        0         0         0       0       1        0     0        0
## Aaliyah      1         0         0       0       1        0     0        0
## Emma         0         0         0       1       1        0     0        0
## Jennifer     0         1         0       0       0        0     0        0
## Olivia       0         1         0       0       0        0     0        1
## Hannah       0         0         0       0       0        0     0        1
## Jessica      0         0         0       0       0        0     0        0
## Sarah        0         0         0       0       0        0     0        0
## Lily         0         0         0       0       0        0     0        0
## Charlotte    0         0         0       0       0        0     0        0
## Elizabeth    0         0         0       0       0        0     0        0
## Abigail      0         0         0       0       0        0     0        0
## Rebecca      0         0         0       0       0        0     0        0
## Samantha     0         0         0       0       0        0     0        0
## Jacob        0         0         0       0       0        0     0        0
## Muhammad     0         0         0       0       0        0     0        0
## Shawn        0         0         0       0       0        0     0        0
## Aaron        0         0         0       0       0        0     0        0
## Daniel       0         0         0       0       0        0     0        0
## Jonah        0         0         0       0       0        0     0        0
## Alex         0         0         0       0       0        0     0        0
## Michael      0         0         0       0       0        0     0        0
## James        0         0         0       0       0        0     0        0
## Ryan         0         0         0       0       0        0     0        0
## Jordan       0         0         0       0       0        0     0        0
## Alexander    0         0         0       0       0        0     0        0
## Ali          0         0         0       0       0        0     0        0
## Tyler        0         0         0       0       0        0     0        0
## Kevin        0         0         0       0       0        0     0        0
## Jack         0         0         0       0       0        0     0        0
## Ethan        0         0         0       0       0        0     0        0
## Luke         0         0         0       0       0        1     1        0
## Harry        1         0         0       0       1        1     1        0
##           Shawn Aaron Daniel Jonah Alex Michael James Ryan Jordan
## Chloe         1     0      1     0    1       0     0    0      0
## Emily         1     0      1     0    1       0     0    0      0
## Aaliyah       0     0      0     0    0       0     0    0      0
## Emma          0     0      0     0    0       0     0    0      0
## Jennifer      0     0      0     0    0       0     0    0      0
## Olivia        0     0      0     0    0       0     0    0      0
## Hannah        0     0      0     0    0       0     0    0      0
## Jessica       0     0      0     0    0       0     0    0      0
## Sarah         0     0      0     0    0       0     0    0      0
## Lily          0     0      0     0    0       0     0    0      0
## Charlotte     0     0      0     0    0       0     0    0      0
## Elizabeth     0     0      0     0    0       0     0    0      0
## Abigail       0     0      0     0    0       0     0    0      0
## Rebecca       0     0      0     0    0       0     0    0      0
## Samantha      0     0      0     0    0       0     0    0      0
## Jacob         0     0      0     0    0       0     0    0      0
## Muhammad      0     0      0     0    0       0     0    0      0
## Shawn         0     0      0     0    0       0     0    0      0
## Aaron         0     0      0     0    0       0     0    0      0
## Daniel        0     0      0     0    0       0     0    0      0
## Jonah         0     0      0     0    0       0     0    0      0
## Alex          0     0      0     0    0       0     0    0      0
## Michael       0     0      0     0    0       0     0    0      0
## James         0     0      0     0    0       0     0    0      1
## Ryan          0     0      0     0    0       0     0    0      1
## Jordan        0     0      0     0    0       0     1    1      0
## Alexander     0     0      0     0    0       0     0    0      0
## Ali           0     0      0     0    0       0     1    1      0
## Tyler         0     0      0     0    0       0     0    0      0
## Kevin         0     0      0     0    0       0     1    0      0
## Jack          0     0      0     0    0       0     0    0      0
## Ethan         0     0      0     0    0       0     0    1      1
## Luke          0     1      0     1    0       1     1    0      0
## Harry         0     1      1     1    0       1     1    0      0
##           Alexander Ali Tyler Kevin Jack Ethan Luke Harry
## Chloe             0   0     0     0    0     1    0     0
## Emily             0   0     0     0    1     0    0     0
## Aaliyah           0   1     1     0    0     0    1     0
## Emma              0   0     0     0    0     0    0     0
## Jennifer          0   0     0     0    0     0    0     0
## Olivia            0   0     0     0    0     0    0     0
## Hannah            0   0     0     0    0     0    0     0
## Jessica           0   0     0     0    0     0    0     0
## Sarah             0   0     0     0    1     0    1     1
## Lily              0   0     0     0    0     0    0     1
## Charlotte         0   0     0     0    0     0    0     0
## Elizabeth         0   0     0     0    0     0    0     0
## Abigail           0   0     0     0    0     0    0     0
## Rebecca           0   0     0     0    0     0    0     1
## Samantha          0   0     0     0    0     0    1     1
## Jacob             0   0     0     0    0     0    1     1
## Muhammad          0   0     0     0    0     0    0     0
## Shawn             0   0     0     0    0     0    0     0
## Aaron             0   0     0     0    0     0    1     1
## Daniel            0   0     0     0    0     0    0     1
## Jonah             0   0     0     0    0     0    1     1
## Alex              0   0     0     0    0     0    0     0
## Michael           0   0     0     0    0     0    1     1
## James             0   1     0     1    0     0    1     1
## Ryan              0   1     0     0    0     1    0     0
## Jordan            0   0     0     0    0     1    0     0
## Alexander         0   0     0     1    0     0    0     1
## Ali               0   0     0     0    0     0    0     1
## Tyler             0   0     0     0    0     1    0     1
## Kevin             1   0     0     0    0     0    1     1
## Jack              0   0     0     0    0     0    1     1
## Ethan             0   0     1     0    0     0    1     1
## Luke              0   0     0     1    1     1    0     1
## Harry             1   1     1     1    1     1    1     0

Exporting out graphs

Sometimes you want to take your subgraphs and use a program like Cytoscape to make the visualization prettier.

Writing to GML format will preserve most of your information.

write_graph(karate, file="karate2.gml", format="gml")

Lots of other output options, including:

cyREST API

The cyREST API allows you to programatically transfer network data into Cytoscape. It’s a bit quirky to set up and use, but once you set it up, you can transfer all network attributes (edge, node, and graph) that you’ve assigned to your GraphNEL objects directly into Cytoscape.

For more info, check this link out: https://github.com/idekerlab/cy-rest-R

Rgraphviz

Custom Node Graphics + KEGGgraph + cluster layout in Rgraphviz

I used a combination of ggplot2 and Rgraphviz to plot time-series data on a pathway defined by KEGG. To get this to work, I had to define some clusters in the graph layout.

mTOR-pathway-Rgraphviz

Drawbacks to Rgraphviz

Graphviz is not guaranteed to give you the best layout - it can take a lot of customization and specification of clusters. You may want to take your networks into a tool such as Cytoscape that will let you customize your graph much more.

More info on customizing graph layout for Rgraphviz here: https://bioconductor.org/packages/release/bioc/vignettes/biocGraph/inst/doc/layingOutPathways.pdf

visNetwork

Make interactive networks with visNetwork and shiny!

Why would you want to do this? Exploratory Data Analysis of the Network.

library(igraph)
karate <- read_graph("data/karate.gml", format="gml")

karate <- set.vertex.attribute(karate, "name", 
                               value=c("Chloe", "Emily", "Aaliyah", "Emma", 
                                       "Jennifer", "Olivia", "Hannah",
                                       "Jessica", "Sarah", "Lily", "Charlotte", 
                                       "Elizabeth", "Abigail", "Rebecca",
                                       "Samantha", "Jacob", "Muhammad", "Shawn", 
                                        "Aaron", "Daniel", "Jonah", "Alex", 
                                       "Michael", "James", "Ryan", "Jordan", 
                                       "Alexander", "Ali", "Tyler", "Kevin", 
                                       "Jack", "Ethan", "Luke", "Harry"))

deg <- igraph::degree(karate)

kInt <- toVisNetworkData(karate)
    
nodes <- kInt$nodes
nodes$label <- rownames(nodes)
nodes$id <- rownames(nodes)

edges <- kInt$edges

  output$network <- renderVisNetwork({
    # minimal example
    visNetwork(nodes, edges, height="600px", width="100%") %>%
      visOptions(highlightNearest = TRUE) %>%
      visInteraction(navigationButtons = TRUE)
  })
  
observe({
  nodes_selection <- names(deg[deg >= min(input$slide_me) & deg <= max(input$slide_me)])
  print(names(nodes_selection))
  print(nodes_selection)
  visNetworkProxy("network") %>%
    visSelectNodes(id = nodes_selection,highlightEdges = TRUE,clickEvent = TRUE)
})

visNetwork objects and igraph objects

I used toVisNetworkData() to convert my igraph karate object to a visNetwork object:

kInt <- toVisNetworkData(karate)

#need to relabel nodes data.frame
nodes <- kInt$nodes
nodes$label <- rownames(nodes)
nodes$id <- rownames(nodes)

edges <- kInt$edges

visNetwork(nodes, edges, height="600px", width="100%") 

Download this Tutorial

github.com/laderast/igraphTutorial/

SessionInfo

sessionInfo()
## R version 3.3.3 (2017-03-06)
## Platform: x86_64-apple-darwin13.4.0 (64-bit)
## Running under: macOS Sierra 10.12.6
## 
## locale:
## [1] en_US.UTF-8/en_US.UTF-8/en_US.UTF-8/C/en_US.UTF-8/en_US.UTF-8
## 
## attached base packages:
## [1] parallel  stats     graphics  grDevices utils     datasets  methods  
## [8] base     
## 
## other attached packages:
## [1] graph_1.52.0        BiocGenerics_0.20.0 shiny_1.0.5        
## [4] visNetwork_2.0.1    knitr_1.17          igraph_1.0.1       
## [7] gridExtra_2.3      
## 
## loaded via a namespace (and not attached):
##  [1] Rcpp_0.12.12    magrittr_1.5    xtable_1.8-2    R6_2.2.2       
##  [5] stringr_1.2.0   tools_3.3.3     grid_3.3.3      gtable_0.2.0   
##  [9] htmltools_0.3.6 yaml_2.1.14     rprojroot_1.2   digest_0.6.12  
## [13] htmlwidgets_0.9 evaluate_0.10.1 mime_0.5        rmarkdown_1.6  
## [17] stringi_1.1.5   backports_1.0.5 stats4_3.3.3    jsonlite_1.5   
## [21] httpuv_1.3.5