简体   繁体   English

使用 ggraph 将 pi 数字绘制为连接束

[英]Plotting pi digits as connection bundles with ggraph

I'm looking to plot the digits of Pi as heirarchical edge bundles, as shown in this image我希望将 Pi 的数字绘制为分层边束,如图所示

在此处输入图像描述

Here, the digits of Pi are grouped by their colour, and then each digit has an edge drawn to the digit that follows it (ie, if Pi is 3.141, then 3 would have an edge drawn to 1, 1 would have an edge to 4, and so on through the digits).在这里,Pi 的数字按其颜色分组,然后每个数字都有一条边连接到它后面的数字(即,如果 Pi 为 3.141,则 3 将有一条边绘制到 1,1 将有一条边连接到它后面的数字) 4,以此类推)。

This is the code I have so far这是我到目前为止的代码

library(ggraph)
library(tidygraph)

dat_lagged <- structure(list(line = c(1L, 3L, 4L, 5L, 6L, 7L), digit = c("3", 
"1", "4", "1", "5", "9"), digit_lagged = c("1", "4", "1", "5", 
"9", "2"), group = c("3", "1", "4", "1", "5", "9")), row.names = c(NA, 
-6L), class = c("tbl_df", "tbl", "data.frame"))

from <- as.numeric(dat_lagged$digit)
to <- as.numeric(dat_lagged$digit_lagged)

ggraph(dat_lagged, 'dendrogram', circular = TRUE) +
  geom_conn_bundle(aes(colour = stat(group)),
                   data = get_con(from, to),
                   edge_alpha = 0.25)

However this is throwing the error然而,这是抛出错误

Error in if (is.numeric(v) && any(v < 0)) { : 
  missing value where TRUE/FALSE needed

Hey I was able to create something similar using a linear layout.嘿,我能够使用线性布局创建类似的东西。 First, create a tbl_graph object from a data.frame with from, to, and the rank of the "from" number.首先,从 data.frame 创建一个 tbl_graph 对象,其中包含 from、to 和“from”数字的等级。

I use library(Rmpfr) to obtain 1000 pi digits for this.我使用library(Rmpfr)为此获得 1000 pi 数字。

library(Rmpfr)
digits <- Const("pi",1000)
#convert to string
pistr <- substr(capture.output(digits)[2],5,nchar(capture.output(digits)[2]))
#reformat string type object to from,to list of lists
reform <- lapply(seq(2,nchar(pistr)),function(x) {c(as.numeric(substr(pistr,x-1,x-1)),as.numeric(substr(pistr,x,x)))})
#bind list of lists to dataframe
do.call(rbind,reform) %>% data.frame -> pi1000
#remove NAs introduced by string of decimal .
pi1000 <- pi1000 %>% slice(-1)
#rename columns 
colnames(pi1000) <- c('from','to')
#reintroduce first connection, 3 -> 1
pi1000$from[1] <- 3
#remove final from,to line with missing "to" number
pi1000 <- pi1000 %>% filter(!is.na(from))
#add a rank for each from, to - we will use this to numerically "jitter" the connections later
pi1000$rank <- seq(1,length(pi1000[,1]))

#next, arrange from,to connections by 'from', so that when tbl_graph is called, nodes are ordered numerically
pi1000 <- pi1000 %>% arrange(from)

#convert from,to DF to tbl_graph
#the tbl_graph's edges are converted so that the from,to now refer to the index of the nodes (i.e. x+1)
piggraph <- pi1000 %>% as_tbl_graph

Once the tbl_graph is formatted as such it becomes easier to create the plot with simpler ggraph grammar, but the plot appears to fall apart when set to circular=T .一旦 tbl_graph 如此格式化,使用更简单的 ggraph 语法创建绘图就变得更容易,但当设置为circular=T时,绘图似乎会分崩离析。 The 'linear' layout lets you control where edges land using a single variable - would love to see an answer that uses a circular format! “线性”布局让您可以使用单个变量控制边缘的位置 - 希望看到使用圆形格式的答案!

piggraph %>% ggraph(layout='linear') + 
    #arc2 creates a plot that can be colored by node by referring to the nodes of the tbl_graph (node.name)
    #add a component rank/length(rank) to make the edges jitter according to when the number happens in pi's sequence
    geom_edge_arc2(aes(x=x+(rank/(length(pi1000$rank))),color=as.factor(node.name))) +
    #add a label for each node and center it with nudge_x
    geom_node_text(aes(label=name),nudge_x = 0.5)

The resulting graph结果图

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM