将匿名函数应用于存储在 R 列表中的 igraph 对象

Apply anonymous function to igraph objects stored in list in R

提问人:HSJ 提问时间:11/12/2023 最后编辑:HSJ 更新时间:11/13/2023 访问量:37

问:

我有 3 个列表(g1、g2、g3),它们彼此包含 10 个图形对象。

每个列表中的图形都有唯一的属性名称,即 g1var、g2var 和 g3var。

## Load packages

library(tidyverse) # Data manipulation
library(igraph) # Base graph manipulation
library(tidygraph) # Drawing graph
library(ggraph) # Drawing graph

## Prepare 10 graphs in 3 lists each other
g1 <- list()
g2 <- list()
g3 <- list()

for (i in 1:10) {
g1 <- append(g1,list(erdos.renyi.game(10, 0.75) %>% as_tbl_graph() %>% activate(nodes) %>% mutate(g1var=sample(1:10, 10, replace=TRUE))))
}

for (i in 1:10) {
g2 <- append(g2,list(erdos.renyi.game(10, 0.5) %>% as_tbl_graph() %>% activate(nodes) %>% mutate(g2var=sample(1:10, 10, replace=TRUE))))
}

for (i in 1:10) {
g3 <- append(g3,list(erdos.renyi.game(10, 0.25) %>% as_tbl_graph() %>% activate(nodes) %>% mutate(g3var=sample(1:10, 10, replace=TRUE))))
}

每个列表中的图形都需要根据动态变量中存储的值进行收缩。我准备了一个匿名函数来运行它。

gid表示图形对象(G1、G2 和 G3)表示存储在图形中的变量(在本例中为 g1var、g2var 和 g3var,但实际数据库包含几列,这些列将根据需要进行更改)var

## Function: contract graphs based on random numbers

fun_contract <- function(gid, var) {

    df <- gid %>% as.data.frame()
    id_contract <- sample(1:10, 10, replace=TRUE)
    df$var <- id_contract # Store values as `contract` accept only vector
    
    contracted <- contract(gid, id_contract, vertex.attr.comb=first) %>% as_tbl_graph()
    
}

最后,我需要通过运行准备好的函数来存储收缩图。 用于将此函数应用于每个列表元素。 并且也被设置。lapplygidvar

## Store contracted graph in list

c1 <- list()
c2 <- list()
c3 <- list()

c1 <- lapply(g1, fun_contract(g1,"g1var"))
c2 <- lapply(g2, fun_contract(g2,"g2var"))
c3 <- lapply(g3, fun_contract(g3,"g3var"))

但它返回一条错误消息,说:

Error in `ensure_igraph()`:
! Must provide a graph object (provided wrong object type).
Run `rlang::last_trace()` to see where the error occurred.

我知道这个错误是由它直接加载对象引起的,而不是列表中的每个图形元素。 表示当前代码中 或 的完整列表。但是我不知道如何根据需要动态更改图表。df <- gid %>% as.data.frame()listgidg1g2g3

另一个问题是如何将收缩图存储在新的空列表中,并且 .c1c2c3

第一个问题可以通过修改来解决,但不确定如何解决。我需要将每个列表元素(图形)转换为数据框才能轻松操作它。df <- gid %>% as.data.frame()

我尝试了一些解决方案,例如通过更改代码来访问FUN中的lapply()索引seq_along()和function():

fun_contract <- function(gid, var, i) {

    df <- gid[[i]] %>% as.data.frame()
    df$var <- sample(1:10, 10, replace=TRUE)
    id_contract <- df$var
    
    contracted <- contract(gid[[i]], id_contract, vertex.attr.comb=first) %>% as_tbl_graph()
    
}

c1 <- lapply(seq_along(g1), fun_contract(g1,"g1var",i))

但它返回了以下错误。根据这篇文章,我知道该函数不接受内部的 branckets。

Error in match.fun(FUN) : 
  'fun_contract(g1, "g1var", i)' is not a function, character or symbol

第二个问题非常令人困惑。我想我可以通过放置类似 的东西将结果图附加到列表中,但应该是动态变量。c1 <- append(c1, c1)c1

非常感谢您解决这些问题的想法..

r l应用 igraph

评论


答: 暂无答案