我有一个包含两列(边缘文件)的数据,它们代表顶点ID,并且连接为
v1,v2
23732,23778
23732,23871
23732,58098
23778,23824
23778,23871
23778,58098
23871,58009
23871,58098
58009,58098
58098,58256
我需要重新格式化它,即顶点ID必须是连续的,并以这样的一个开头
v1,v2
1,2
1,3
1,4
2,5
2,3
2,4
3,5
3,4
5,4
4,6
有人可以建议如何自动执行吗? 另外,我需要同时具有原始ID和新ID的转换表。 感谢您的支持。
答案 0 :(得分:1)
这是另一种使用factor()
进行重新编号的方法:
library(data.table)
# reshape from wide to long format using row numbers
tmp <- melt(setDT(DT)[, rn := .I], "rn", value.name = "old")[
# create new ids from factor levels
, new := as.integer(factor(old))][]
# reshape back to wide format again
dcast(tmp, rn ~ variable, value.var = "new")[, -"rn"]
v1 v2 1: 1 2 2: 1 4 3: 1 6 4: 2 3 5: 2 4 6: 2 6 7: 4 5 8: 4 6 9: 5 6 10: 6 7
可以通过以下方式创建翻译表
tmp[, unique(.SD), .SDcols = c("old", "new")]
old new 1: 23732 1 2: 23778 2 3: 23871 4 4: 58009 5 5: 58098 6 6: 23824 3 7: 58256 7
为了精确地再现 OP的新编号,我们需要使用fct_inorder()
包中的forcats
函数重新排列因子水平:
tmp <- melt(DT[, rn := .I], "rn", value.name = "old")[
order(rn, variable), new := as.integer(forcats::fct_inorder(factor(old)))][]
dcast(tmp, rn ~ variable, value.var = "new")[, -"rn"]
v1 v2 1: 1 2 2: 1 3 3: 1 4 4: 2 5 5: 2 3 6: 2 4 7: 3 6 8: 3 4 9: 6 4 10: 4 7
然后,翻译变成
old new 1: 23732 1 2: 23778 2 3: 23871 3 4: 58009 6 5: 58098 4 6: 23824 5 7: 58256 7
library(data.table)
DT <- fread(
"v1,v2
23732,23778
23732,23871
23732,58098
23778,23824
23778,23871
23778,58098
23871,58009
23871,58098
58009,58098
58098,58256"
)
答案 1 :(得分:0)
这不是您真正想要的,因为我在分配ID之前对节点名称进行了排序。
我选择做的是获取所有唯一的节点ID,对它们进行排序,然后将每个ID分配给一个整数。
df <- structure(list(v1 = c(23732L, 23732L, 23732L, 23778L, 23778L,
23778L, 23871L, 23871L, 58009L, 58098L), v2 = c(23778L, 23871L,
58098L, 23824L, 23871L, 58098L, 58009L, 58098L, 58098L, 58256L
)), .Names = c("v1", "v2"), class = "data.frame", row.names = c(NA,
-10L))
# Put nodes in ascending order
df <- df[order(df$v1, df$v2), ]
# create a mapping of node number to node ID (as a vector)
# All unique nodes between the two columns, sorted
node_names <- sort(unique(c(df$v1, df$v2)))
# a vector of integers from 1 to length(node_names)
node_id <- seq_along(node_names)
# assign (map) the node names to the integer values
names(node_id) <- node_names
# Add the node IDs to df
df$v1_id <- node_id[as.character(df$v1)]
df$v2_id <- node_id[as.character(df$v2)]
df
v1 v2 v1_id v2_id
1 23732 23778 1 2
2 23732 23871 1 4
3 23732 58098 1 6
4 23778 23824 2 3
5 23778 23871 2 4
6 23778 58098 2 6
7 23871 58009 4 5
8 23871 58098 4 6
9 58009 58098 5 6
10 58098 58256 6 7