2

我有以下来自贝叶斯网络学习算法的字符串(如来自bnlearndeal包):

[1] "[wst|af:bq:rloss_s:pre3][af|bq][d|wst:af:con:rloss_s][bq|con][con|af][rloss_s|af:con:pre3][pre3|af:con]"

该字符串定义了变量之间的连接以及连接的方向。括号( )中每一项的第一个变量[...]代表一个节点,后面的所有变量|代表在方向上连接到第一个节点的节点。这些变量由 分隔:

我想将字符串转换为表示每个变量之间连接的 data.frame。它应该如下所示:

> data.frame(string_table)
      from      to
1       af     wst
2       bq     wst
3  rloss_s     wst
4     pre3     wst
5       bq      af
6      wst       d
7       af       d
8      con       d
9  rloss_s       d
10     con      bq
11      af     con
12      af rloss_s
13     con rloss_s
14    pre3 rloss_s
15      af    pre3
16     con    pre3
4

2 回答 2

4

我会在这里使用图形工具而不是字符串操作。这是一个例子来说明

library(bnlearn)

d = clgaussian.test
m = hc(d)

所以你有字符串/模型

bnlearn::modelstring(m)
#[1] "[A][B][C][H][D|A:H][F|B:C][E|B:D][G|A:D:E:F]"

使用bnlearn循环获取每个节点的父节点

stack(sapply(nodes(m), function(x) parents(m, x)))

igraph在邻接矩阵上使用以获取边缘列表

library(igraph)
as_edgelist(graph_from_adjacency_matrix(amat(m)))

编辑:

似乎bnlearn具有提取边缘的功能

arcs(m)
于 2017-05-01T20:51:55.580 回答
3

您可以分两步执行此操作。首先,使用正则表达式(例如str_match_allstringr 包中的函数)提取对矩阵:

s <- "[wst|af:bq:rloss_s:pre3][af|bq][d|wst:af:con:rloss_s][bq|con][con|af][rloss_s|af:con:pre3][pre3|af:con]"

library(stringr)
m <- str_match_all(s, "\\[(.*?)\\|(.*?)\\]")[[1]]
m

这导致了这个矩阵,其中第三和第二列有我们感兴趣的内容:

     [,1]                       [,2]      [,3]                
[1,] "[wst|af:bq:rloss_s:pre3]" "wst"     "af:bq:rloss_s:pre3"
[2,] "[af|bq]"                  "af"      "bq"                
[3,] "[d|wst:af:con:rloss_s]"   "d"       "wst:af:con:rloss_s"
[4,] "[bq|con]"                 "bq"      "con"               
[5,] "[con|af]"                 "con"     "af"                
[6,] "[rloss_s|af:con:pre3]"    "rloss_s" "af:con:pre3"       
[7,] "[pre3|af:con]"            "pre3"    "af:con"            

然后,将它们添加到数据框中,将“从”值拆分为冒号,并使用 tidyrunnest()为每个从到对创建一行。

library(tidyr)
df <- data.frame(from = m[, 3], to = m[, 2])
string_table <- unnest(df, from = str_split(from, ":"))
于 2017-05-01T20:43:08.473 回答