TraMineR与seqHMM绘图布局异常:如何单页展示4幅图
TraMineR序列分布图与HMM图布局异常解决
问题背景
使用TraMineR绘制2幅序列分布图(seqplot(type='d')),并在下方对应绘制2个隐马尔可夫模型(HMM)图,通过layout()设置2行2列布局后,前3幅图能正常显示,但第4幅HMM图会跳转到新页面,导致右下角区域留白。
可复现代码:
library('seqHMM') library('TraMineR') data("biofam") biofam <- biofam[sample(nrow(biofam),300),] biofam.lab <- c("Parent", "Left", "Married", "Left+Marr", "Child", "Left+Child", "Left+Marr+Child", "Divorced") biofam.seq <- seqdef(biofam, 10:25, labels=biofam.lab) ### Fit a Hidden Markov Model biofam.hmm <- build_hmm(observations = biofam.seq, n_states = 3) ### 尝试布局绘图 layout(matrix(c(1,2,3,4), ncol = 2, byrow = TRUE)) layout.show(4) par(cex = 0.65, mar = c(2.5,4.1,2.5,1.5)) ### 序列分布图 seqplot(biofam.seq, type = 'd', with.legend = FALSE, border = NA, ylab = NA) seqplot(biofam.seq, type = 'd', with.legend = FALSE, border = NA, ylab = NA) ### HMM图 par(cex = 0.5, mar = c(1.5,3.5,3.5,1.5)) plot(biofam.hmm, with.legend = FALSE, vertex.size = 15) plot(biofam.hmm, with.legend = FALSE, vertex.size = 15)
问题原因
TraMineR的seqplot基于基础绘图系统,而seqHMM的plot.bhmm方法(绘制HMM)基于grid绘图系统,两个系统的布局管理不兼容。layout()仅对基础绘图系统生效,当绘制第一个HMM图时,grid系统会重置绘图设备,导致后续的HMM图无法进入预设的layout区域。
解决方法
方法1:用gridBase协调双绘图系统
使用gridBase包让HMM图正确嵌入layout指定的区域,具体代码如下:
library('seqHMM') library('TraMineR') library(grid) library(gridBase) data("biofam") biofam <- biofam[sample(nrow(biofam),300),] biofam.lab <- c("Parent", "Left", "Married", "Left+Marr", "Child", "Left+Child", "Left+Marr+Child", "Divorced") biofam.seq <- seqdef(biofam, 10:25, labels=biofam.lab) biofam.hmm <- build_hmm(observations = biofam.seq, n_states = 3) ### 设置2行2列布局 layout(matrix(c(1,2,3,4), ncol = 2, byrow = TRUE)) # 绘制第一幅序列图 par(cex = 0.65, mar = c(2.5,4.1,2.5,1.5)) seqplot(biofam.seq, type = 'd', with.legend = FALSE, border = NA, ylab = NA) # 绘制第二幅序列图 seqplot(biofam.seq, type = 'd', with.legend = FALSE, border = NA, ylab = NA) # 绘制第一幅HMM图 par(cex = 0.5, mar = c(1.5,3.5,3.5,1.5)) grid.newpage() vps <- baseViewports() pushViewport(vps$inner, vps$figure, vps$plot) plot(biofam.hmm, with.legend = FALSE, vertex.size = 15) popViewport(3) # 绘制第二幅HMM图 grid.newpage() vps <- baseViewports() pushViewport(vps$inner, vps$figure, vps$plot) plot(biofam.hmm, with.legend = FALSE, vertex.size = 15) popViewport(3)
方法2:用gridExtra统一转为grid对象布局
将所有图转换为grid对象,通过gridExtra::grid.arrange()统一管理布局:
library('seqHMM') library('TraMineR') library(grid) library(gridExtra) library(gridGraphics) data("biofam") biofam <- biofam[sample(nrow(biofam),300),] biofam.lab <- c("Parent", "Left", "Married", "Left+Marr", "Child", "Left+Child", "Left+Marr+Child", "Divorced") biofam.seq <- seqdef(biofam, 10:25, labels=biofam.lab) biofam.hmm <- build_hmm(observations = biofam.seq, n_states = 3) # 将序列图转为grid对象 seq1 <- grid.grabExpr({ par(cex = 0.65, mar = c(2.5,4.1,2.5,1.5)) seqplot(biofam.seq, type = 'd', with.legend = FALSE, border = NA, ylab = NA) }) seq2 <- grid.grabExpr({ par(cex = 0.65, mar = c(2.5,4.1,2.5,1.5)) seqplot(biofam.seq, type = 'd', with.legend = FALSE, border = NA, ylab = NA) }) # 将HMM图转为grid对象 hmm1 <- grid.grabExpr({ plot(biofam.hmm, with.legend = FALSE, vertex.size = 15) }) hmm2 <- grid.grabExpr({ plot(biofam.hmm, with.legend = FALSE, vertex.size = 15) }) # 2行2列布局 grid.arrange(seq1, seq2, hmm1, hmm2, ncol=2)
内容的提问来源于stack exchange,提问作者BossVom Schloss
相关产品推荐
相关产品推荐

