我是一个使用R进行社交网络分析的基本程序员,并且有一些不确定如何解决的信息。
我有什么:
- 存储为 csv 文件的邻接矩阵,其中包含以下信息:a) 第 1 行的家庭和第 1 列的家庭通过共享资源相互交流。b) 互动是由亲属数表示的纽带。数字越小,亲属关系越近(或越强)。例如,1是亲子亲属,100是没有亲属关系。与自己没有亲缘关系是NA。c) 文件片段:
[,1] [,2] [,3] [,4] [,5] [1,] NA 100 2 1 100 [2,] 4 NA 100 100 3 [3,] 100 3 NA 2 4 [4,] 100 1 5 NA 100 [5,] 1 100 4 100 NA
我需要什么:
-
我需要将此邻接矩阵转换为包含三列("HH1"、"HH2"、"HHKinRank")的边缘列表,以便完成额外的亲属关系计算。
-
此边缘列表必须另存为新的 csv 文件以供进一步分析。
-
我对列表的最大问题是,它只需要列出数值。如果没有平局(NA),那么边缘列表会显示这一点吗?
我做了什么:
我尝试将 csv 文件分配给新变量HHKinRank.el <- read.csv("HouseholdKinRank.csv").
当我这样做时,最令人沮丧的组件是确定我可能必须使用哪些库。有许多函数命令,例如 melt,因此故障排除是一个问题,因为我也可能错误地分配值。
我可以从边缘列表转到矩阵,但相反的情况很难运行命令。
感谢您对此的任何帮助。
R 的 network
包执行此操作,可能也可以在 igraph
中执行此操作。
library(network)
# create the example data
adjMat <- matrix(c(NA, 100, 2, 1, 100,
4, NA, 100, 100, 3,
100, 3, NA, 2, 4,
100, 1, 5, NA, 100,
1, 100, 4, 100, NA),
ncol = 5,byrow=TRUE)
# create a network object
net<-as.network(adjMat,matrix.type='adjacency',
ignore.eval = FALSE, # read edge values from matrix as attribute
names.eval='kinship', # name the attribute
loops=FALSE) # ignore self-edges
# convert to an edgelist matrix
el <-as.edgelist(net,attrname = 'kinship')
# relabel the columns
colnames(el)<-c("HH1", "HH2", "HHKinRank")
# check results
el
HH1 HH2 HHKinRank
[1,] 1 2 100
[2,] 1 3 2
[3,] 1 4 1
[4,] 1 5 100
[5,] 2 1 4
[6,] 2 3 100
[7,] 2 4 100
[8,] 2 5 3
[9,] 3 1 100
[10,] 3 2 3
[11,] 3 4 2
[12,] 3 5 4
[13,] 4 1 100
[14,] 4 2 1
[15,] 4 3 5
[16,] 4 5 100
[17,] 5 1 1
[18,] 5 2 100
[19,] 5 3 4
[20,] 5 4 100
# write edgelist matrix to csv file
write.csv(el,file = 'myEdgelist.csv')
原始数据:
adj_mat <- matrix(
c(NA, 100, 2, 1, 100,
4, NA, 100, 100, 3,
100, 3, NA, 2, 4,
100, 1, 5, NA, 100,
1, 100, 4, 100, NA
),
nrow = 5, ncol = 5, byrow = TRUE
)
adj_mat
#> [,1] [,2] [,3] [,4] [,5]
#> [1,] NA 100 2 1 100
#> [2,] 4 NA 100 100 3
#> [3,] 100 3 NA 2 4
#> [4,] 100 1 5 NA 100
#> [5,] 1 100 4 100 NA
1) 将行索引、列索引和邻接矩阵的值组合成 3 个矩阵的列表:
rows_cols_vals_matrices <- list(row_indices = row(adj_mat),
col_indices = col(adj_mat),
values = adj_mat)
rows_cols_vals_matrices
#> $row_indices
#> [,1] [,2] [,3] [,4] [,5]
#> [1,] 1 1 1 1 1
#> [2,] 2 2 2 2 2
#> [3,] 3 3 3 3 3
#> [4,] 4 4 4 4 4
#> [5,] 5 5 5 5 5
#>
#> $col_indices
#> [,1] [,2] [,3] [,4] [,5]
#> [1,] 1 2 3 4 5
#> [2,] 1 2 3 4 5
#> [3,] 1 2 3 4 5
#> [4,] 1 2 3 4 5
#> [5,] 1 2 3 4 5
#>
#> $values
#> [,1] [,2] [,3] [,4] [,5]
#> [1,] NA 100 2 1 100
#> [2,] 4 NA 100 100 3
#> [3,] 100 3 NA 2 4
#> [4,] 100 1 5 NA 100
#> [5,] 1 100 4 100 NA
2) 展平矩阵:
vectorized_matrices <- lapply(rows_cols_vals_matrices, as.vector)
vectorized_matrices
#> $row_indices
#> [1] 1 2 3 4 5 1 2 3 4 5 1 2 3 4 5 1 2 3 4 5 1 2 3 4 5
#>
#> $col_indices
#> [1] 1 1 1 1 1 2 2 2 2 2 3 3 3 3 3 4 4 4 4 4 5 5 5 5 5
#>
#> $values
#> [1] NA 4 100 100 1 100 NA 3 1 100 2 100 NA 5 4 1 100
#> [18] 2 NA 100 100 3 4 100 NA
3) 将向量绑定成 3 列矩阵:
melted <- do.call(cbind, vectorized_matrices)
head(melted)
#> row_indices col_indices values
#> [1,] 1 1 NA
#> [2,] 2 1 4
#> [3,] 3 1 100
#> [4,] 4 1 100
#> [5,] 5 1 1
#> [6,] 1 2 100
4) 删除第 3 列为 NA 的行:
filtered <- melted[!is.na(melted[, 3]), ]
filtered
#> row_indices col_indices values
#> [1,] 2 1 4
#> [2,] 3 1 100
#> [3,] 4 1 100
#> [4,] 5 1 1
#> [5,] 1 2 100
#> [6,] 3 2 3
#> [7,] 4 2 1
#> [8,] 5 2 100
#> [9,] 1 3 2
#> [10,] 2 3 100
#> [11,] 4 3 5
#> [12,] 5 3 4
#> [13,] 1 4 1
#> [14,] 2 4 100
#> [15,] 3 4 2
#> [16,] 5 4 100
#> [17,] 1 5 100
#> [18,] 2 5 3
#> [19,] 3 5 4
#> [20,] 4 5 100
5)将其全部包装成一个函数:
as_edgelist.adj_mat <- function(x, .missing = NA) {
# if there arerow/colnames or non-numeric data, you'll need to to use a data frame to
# handle heterogenous data types
stopifnot(is.numeric(x) & is.null(dimnames(x)))
melted <- do.call(cbind, lapply(list(row(x), col(x), x), as.vector))
if (is.na(.missing)) {
out <- melted[!is.na(melted[, 3]), ]
} else {
out <- melted[melted[, 3] != .missing, ]
}
out
}
6)试一试:
as_edgelist.adj_mat(adj_mat)
#> [,1] [,2] [,3]
#> [1,] 2 1 4
#> [2,] 3 1 100
#> [3,] 4 1 100
#> [4,] 5 1 1
#> [5,] 1 2 100
#> [6,] 3 2 3
#> [7,] 4 2 1
#> [8,] 5 2 100
#> [9,] 1 3 2
#> [10,] 2 3 100
#> [11,] 4 3 5
#> [12,] 5 3 4
#> [13,] 1 4 1
#> [14,] 2 4 100
#> [15,] 3 4 2
#> [16,] 5 4 100
#> [17,] 1 5 100
#> [18,] 2 5 3
#> [19,] 3 5 4
#> [20,] 4 5 100