美化ggplot2生成的原始图片至清爽可出版的样子
针对于ggplot2的可视化教程网上有很多,展示了很多ggplot2的图示,根据代码照猫画虎我们都可以去复原,但复原出来的图会有一些粗糙感。如何优雅的将这些图形应用到生产实际中呢,网上的资料并没有系统的说明,那今天来演示一下,希望起到抛砖引玉的作用。
在数据分析领域,数据可视化是数据分析师所需具备的一个很重要的技能,论便捷程度excel作图当属第一,但涉及到图形多样性及可定制性的话,R语言和python 是首当其冲的好工具。由于工作需要,笔者经常需要多个工具切换使用,个人认为在可视化上还是R语言更胜python一筹,本文主要由R语言的ggplot2包说起,当然所碰到的问题也是从ggplot2开始。
背景
咱们还是先假定一个场景。有以下的数据,需要展示出每日各个水果的销量(sold_amount),及购买用户数(customers)。考虑到图形传递信息的丰富度,我们用ggplot2来执行这项任务。
笔者刚接触ggplot2时也惊叹于他的各种示例图片,但实际工作中,又发现这些示例又有一些华而不实,想象一下借助ggplot2的示例,如果你把图做成这样放到你的汇报或总结里, 可能会有一些尴尬,懂得人知道你确实用到了很多的ggplot知识,不懂得人可能就会说,这图好丑呀?好吧 确实很丑,而且你用到了这些知识但没用好等于不会
library(ggplot2) ##做图
library(reshape2) ##揉数据data <- read.table('clipboard',header = TRUE,stringsAsFactors = FALSE) #将长条形数据读入,这里直接用剪切板读了。
data$date <- as.Date(data$date,'%m/%d') #将日期列识别出来
data_melt <- melt(data,id.vars = c("date","goods_type")) #需要把数据揉成ggplot所需要的长表数据:日期列(date),水果名(goods_type),变量列(销量,顾客数),变量对应的值
head(data_melt)
##ggplot的常规默认作图
p <- ggplot(data_melt,aes(date,value,group = goods_type,color=goods_type)) + ##基本图形元素 geom_line()+ ##加入线形facet_grid(variable~.,scales = 'free_y')+ ##调整分图y轴值范围scale_x_date(date_breaks = "1 day", date_labels = "%m-%d")+ ##设置x轴lab的样式theme(axis.text.x=element_text(angle=60, hjust=1)) ##设置x轴lab的位置和间距。
p
解决方案
咱们先来分析一下,这个图为什么会丑。
- 首先从整体上来说,ggplot2的默认风格可能各大部分的实际场景都不是那么的搭配。
- 由于数据的波动较大(随机生成的数据没办法),线条是很零乱的,仔细去分析的话,线条也能反应出销量和用户数的变化,但是分析师出产的应该是让人容易接受的优美的东西,所以能不能呈现优雅的凌乱?
- 整体布局,字体和图形元素位置的调整
- 分辨率问题,这个我觉得挺影响观赏效果。
实操
-
针对第一个问题:很好解决,ggplot2有很多主题供我们选择,这里我们选择theme_light,看下效果先:
###美化后 +theme p <- ggplot(data_melt,aes(date,value,group = goods_type,color=goods_type)) + geom_line()facet_grid(variable~.,scales = 'free_y')+scale_x_date(date_breaks = "1 day", date_labels = "%m-%d")+theme_light()+ ###调用ggplot自带的一些theme theme(axis.text.x=element_text(angle=60, hjust=1)) p
-
针对第二个问题:我们参考excel的点线图去做,也很优雅。看看效果:
##+点线 p <- ggplot(data_melt,aes(date,value,group = goods_type,color=goods_type)) + geom_line(linetype="solid",size=0.8)+ ##更改线型 线粗geom_point(size=2)+ ##加入点 并调整点的大小facet_grid(variable~.,scales = 'free_y')+scale_x_date(date_breaks = "1 day", date_labels = "%m-%d")+theme_light()+theme(axis.text.x=element_text(angle=60, hjust=1)) p
-
针对第三个问题:就得看自己的审美了。调整布局,字体,图例类型 及摆放位置,再加上一些标题,副标题。
##美化后。+修改字体,及图例位置 p <- ggplot(data_melt,aes(date,value,group = goods_type,color=goods_type)) + geom_line(linetype="solid",size=1.2)+geom_point(size=2)+facet_grid(variable~.,scales = 'free_y')+scale_x_date(date_breaks = "1 day", date_labels = "%m-%d")+theme_light()+theme(axis.text.x=element_text(angle=60, hjust=1))+ggtitle("Daily data of goods_type\n")+xlab("Date") + ylab("Value")+theme(##图形标题设置 字体和大小plot.title = element_text(family='Times', face='bold.italic',size = 36),##x坐标轴axis.title.x = element_text(family = 'Times',face = 'bold',size =27),##y坐标轴axis.title.y = element_text(family = 'Times',face = 'bold',size=27),##图例标题legend.title = element_text(family = 'Times',face = 'bold',size=26),##图例内的字体legend.text = element_text(family = 'Times',face = 'bold',size=20),##分面或分幅字体strip.text = element_text(family = 'Times',face = 'bold.italic',size=27),##图例位置legend.position="bottom") p
- 针对第四个问题:Rstudio提供了很好的设置图形大小的工具,也可以直接导出为矢量图的形式,这样更保真。不过我在日常工作中经常会使用先保存为pdf的形式,然后通过pdf工具导出相应的图,大家有空可以试一下,我常用的设置是导出为横向A4纸大小的pdf,然后通过pdf工具导出相应分辨率(最好300dpi以上)的图片,出来的效果如下:
小结
当然,这个分享主要是针对于对R语言的ggplot2包 或python里的ggplot2包有了解的同学,关于ggplot2有很多有用和好用的东西值得去钻研和分享,希望大家共同努力。