Keywords: Network analysis, network application, visualization.
This post introduces one way to visualize networks using the package igraph. It is fairly straightforward, the steps we need to take are:
Essentially, the content in this network project is used to analyze local hazards risk reduction focusing on stakeholders’ collaborative activities and co-worked experience. The network of plans illustrate the extent that existing plan documents are integrated for informed decision making. The network of people demonstrate the types of agency, the frequency of co-working experience, and the depth of conversation in local risk reduction.
Find more information here for the published article if you are interested. Below are step-by-step network visualization.
You may find examples of edges and nodes in txt format in source file.
edges <- read.csv("link.csv")
nodes <- read.csv("node.csv")
[1] 136
[1] 126
net <- graph_from_data_frame(d=links, vertices=nodes, directed=F)
# If you have extra attributes in your edge and vertices as appeared in your data collection,
#you may add them to the edge and vertices. Four instance, the vertex here shows the stakeholders' agency names.
#The type of the edge also represents the type of meeting that get stakeholders connected.
E(net)$type
[1] "lup" "rec" "mit" "rec" "mit" "rec" "mit" "res" "mit" "res"
[11] "mit" "mit" "lup" "mit" "mit" "mit" "mit" "res" "res" "res"
[21] "res" "res" "res" "lup" "rec" "rec" "mit" "rec" "mit" "mit"
[31] "mit" "mit" "mit" "mit" "mit" "mit" "mit" "mit" "mit" "mit"
[41] "mit" "mit" "mit" "mit" "res" "mit" "res" "mit" "mit" "mit"
[51] "mit" "mit" "mit" "res" "res" "res" "res" "res" "res" "res"
[61] "res" "mit" "mit" "mit" "mit" "mit" "mit" "res" "res" "res"
[71] "res" "res" "res" "mit" "mit" "mit" "mit" "mit" "mit" "mit"
[81] "mit" "mit" "mit" "mit" "mit" "mit" "mit" "mit" "res" "res"
[91] "res" "res" "res" "res" "res" "res" "res" "res" "res" "res"
[101] "res" "res" "res" "res" "res" "res" "res" "res" "res" "res"
[111] "res" "res" "res" "res" "res" "res" "res" "res" "res" "res"
[121] "res" "res" "res" "res" "res" "res" "res" "res" "res" "res"
[131] "res" "res" "res" "res" "res" "res"
V(net)$agency #vertex attribute "agency name"
[1] "CoPlanning" "CoLegislative" "CoBudget" "CoPublicWork"
[5] "CoEM" "StateEM" "CoStormwater" "CoExecutive"
[9] "CoInfo" "CoBuilding" "Insurance" "DisasterSpec"
[13] "HigherEdu" "NOAA" "USACE" "StateResource"
[17] "DisasterSpec2" "Consultant1"
#find specific nodes
V(net)[agency == "CoPlanning"]
+ 1/18 vertex, named, from 438c3e6:
[1] s01
#specific planning type
E(net)[type =="lup"]
+ 3/136 edges from 438c3e6 (vertex names):
[1] s01--s02 s01--s10 s02--s10
# Scale the layout by 5 to increase distance between nodes
layout <- layout_with_fr(net) * 5
plot(net,
layout = layout,
edge.color="grey",
vertex.color="orange",
vertex.frame.color="#ffffff",
vertex.label.cex=.6,
vertex.label=V(net)$agency,
vertex.label.color="black")
# This plot is to visualize actors based on type (e.g., county, state, fed, private, nonprofit, private)
# set attributes is to add them to the igraph object
# Generate colors based on agency type:
colrs <- c("antiquewhite2", "grey", "gold", "coral","aquamarine")
V(net)$color <- colrs[V(net)$agency.type]
E(net)$color <- as.factor(links$type)
# Compute node degrees (#links) and use that to set node size:
deg <- degree(net, mode="all")
V(net)$size <- deg*3
# use the influence weight for nodes:
V(net)$size <- V(net)$influence*2.2
# Setting them to NA will render no labels:
V(net)$label <- NA
# Set edge width based on weight:
E(net)$width <- E(net)$weight
#change arrow size and edge color:
#E(net)$arrow.size <- .2
E(net)$edge.color <- "azure4"
E(net)$width <- 1+E(net)$weight*.8
# Scale the layout to increase edge length
layout <- layout_with_fr(net)
scaled_layout <- layout * 2
plot(net,
vertex.frame.color="#ffffff",
vertex.label.cex=.6,
vertex.label=V(net)$agency,
vertex.label.color="black",
layout = scaled_layout)
# Adjustment to the legend
legend("right", c("Local Agency","State Agency", "Federal Agency", "Private Sector", "Nonprofit"), pch=21,
col="#777777", pt.bg=colrs, pt.cex=2, cex=.8, bty="n", ncol=1)
s01 s02 s03 s04 s05 s06
31 2 3 13 13 26
# Calculate the closeness centrality for each node
clo_1 <- closeness(net, vids = V(net), normalized = F)
head(clo_1)
s01 s02 s03 s04 s05 s06
0.05555556 0.03125000 0.03225806 0.04347826 0.04166667 0.05263158
# Calculate the betweenness centrality for each node
bet_1 <- betweenness(net, normalized = F)
head(bet_1)
s01 s02 s03 s04 s05 s06
27.300000 0.000000 0.000000 3.041667 1.850000 9.241667