ggplot2是R语言中用来可视化的利器,其图层逻辑非常人性化,简单的说就是一句话一张图,后一张图叠加在前一张图上,所想表达的几乎都可以用一句代码在图形上展示出来。如果刚开始接触R作图的话,完全可以快速地从ggplot2入门而不用去管base作图,ggplot2的用法已经完全覆盖base作图,除了一项(我至今接触到的)——图片布局
刚开始我也曾困惑过,base作图有par()
函数来对多张图片进行布局排布,但该函数对于ggplot2的作图结果则是完全无效的。然后网上搜了一通,找了个grid
包,其可以说专门用来排版图片的,当然也支持ggplot2,但是个人感觉使用起来不太顺手(由于其功能有点复杂了)。最近刚看到一个函数multiplot
,查了下是来自Rmisc
包,这个包发布于2013年,我在这之前也没用过,但是这个函数对于ggplot2结果图片的排布来说简单好使(后来简单看了下multiplot
函数的源码,原来其就是用了grid
包来实现布局的。。。相当于将grid
包中关键的部分又封装了下),下面记录下上述两种方法: 先找一个测试集数据,查了下R自带的数据集,最后选用airquality数据集,其记录了纽约1973年5-9月份每日空气质量,如测量对象有Ozone
,Solar.R
,Wind
,Temp
data <- airquality
names(data)
#[1] "Ozone" "Solar.R" "Wind" "Temp" "Month" "Day"
我想用箱线图展示每个月份下上述4个测量值的变化,那么可以用代码一张一张分别作图,也可以用lapply
函数进行循环作图,为了代码的整洁肯定选用后者
vars <- names(data)[1:4]
p <- lapply(vars, function(x){
ggplot(data, aes(x = Month, y = eval(parse(text = x)), fill = Month)) +
geom_boxplot(na.rm = T) +
labs(y = x, title = paste0(x, " In Different Months")) +
theme_light() +
theme(plot.title = element_text(hjust = 0.5)) +
guides(fill = "none")
})
这里有个小技巧,通常如果将function(x)中的x(x这里的类型是字符串)直接作为ggplot2的y变量的值是不行的,需要对x做个转化,这里就用了parse
和eval
函数,前者将x类型转化为表达式(但不求解),后者则是对表达式求解,我也是长见识了
p为列表,p[[1]]
代表第一张图
用Rmisc包的multiplot函数
首先用最简单的方法做两张图
multiplot(plotlist = p[1:4], cols = 2)
multiplot(plotlist = p[1:3], cols = 3)
这里
col
表示每列的图片数目我们还可以通过
layout
参数来设定图片的排布矩阵,如:multiplot(plotlist = p[1:3], layout = matrix(c(1,2,3,3), nrow = 2))
multiplot(plotlist = p[1:3], layout = matrix(c(1,2,3,3), nrow = 2, byrow = T))
是不是很方便。。。。
用grid包的viewport函数
grib包的viewport函数可以画上面的所有布局的图(PS.multiplot函数本来就是调用grib包的,所以当然都可以画出来),但是有一种形式是multiplot函数无法比较方便的实现,但viewport函数可以(主要还是multiplot函数没封装完全,我看了下,重新改下函数,还是可以实现的),如下
先pushViewport设定一个空白画布,然后用pushViewport函数布局(主要用来设定后续viewport的可放置的位置)
library(grid) grid.newpage() pushViewport(viewport(layout = grid.layout(3,4)))
然后用print输出图片
print(p[[1]], vp = viewport(layout.pos.row = 1:3, layout.pos.col = 1)) print(p[[2]], vp = viewport(layout.pos.row = 1, layout.pos.col = 2:3)) print(p[[3]], vp = viewport(layout.pos.row = 3, layout.pos.col = 2:3)) print(p[[4]], vp = viewport(layout.pos.row = 1:3, layout.pos.col = 4))
如果上述图片要用multiplot函数来实现,则需要这样写,PS.这矩阵写的好绕,还是viewport显得简洁了
multiplot(plotlist = p[1:4], layout = matrix(c(1,2,2,4,1,0,0,4,1,3,3,4), nrow = 3, byrow = T))
参考资料:
R统计绘图(2):grid布局
扎心实战案例:麻(shi)雀(zhan)虽小,五脏俱全
本文出自于http://www.bioinfo-scrounger.com转载请注明出处