这是关于此问题的后续问题:R: plot multiple lines in one graph
在那里,我使用了部分数据来绘制多行图形。现在我想在一个网格中绘制多个图形,因为我已经对数据进行了分组。
现在我正在这样做,为每组数据创建数据帧,然后为每个数据帧创建一个图表,并使用gridd.arrange()
组合这些数据帧
但是,我想知道我是否可以将分组数据作为1个数据集处理,而不是创建所有这些单独的表?
我的数据结构如下:
Category1 Category2 Category3
Company 2011 2013 2011 2013 2011 2013
Company1 300 350 290 300 295 290
Company2 320 430 305 301 300 400
Company3 310 420 400 305 400 410
那么有没有办法立即处理这个问题并绘制3个图表(每个类别)以及每个公司年度(2011年和2013年)的行?
答案 0 :(得分:5)
您一定要学习如何构建数据以及如何make a reproducable example。以这种非结构化格式处理数据真的很难。不仅是为了你,也为了我们。
mdf <- read.table( text="Company 2011 2013 2011 2013 2011 2013
Company1 300 350 290 300 295 290
Company2 320 430 305 301 300 400
Company3 310 420 400 305 400 410", header = TRUE, check.names=FALSE )
library("reshape2")
cat1 <- melt(mdf[c(1,2,3)], id.vars="Company", value.name="value", variable.name="Year")
cat1$Category <- "Category1"
cat2 <- melt(mdf[c(1,4,5)], id.vars="Company", value.name="value", variable.name="Year")
cat2$Category <- "Category2"
cat3 <- melt(mdf[c(1,6,7)], id.vars="Company", value.name="value", variable.name="Year")
cat3$Category <- "Category3"
mdf <- rbind(cat1, cat2, cat3)
head(mdf)
Company Year value Category
1 Company1 2011 300 Category1
2 Company2 2011 320 Category1
3 Company3 2011 310 Category1
4 Company1 2013 350 Category1
5 Company2 2013 430 Category1
6 Company3 2013 420 Category1
如果类别数量非常大,这当然可以自动化:
library( "plyr" )
mdf <- adply( c(1:3), 1, function( cat ){
tmp <- melt(mdf[ c(1, cat*2, cat*2+1) ], id.vars="Company", value.name="value", variable.name="Year")
tmp$Category <- paste0("Category", cat)
return(tmp)
} )
但如果你可以避免从一开始就反复推送所有这些数据,你应该这样做。
ggplot2
内置支持显示相同类型数据的分面图,如果它们可以是一个(或多个)变量的子集。请参阅? facet_wrap
或? facet_grid
。
ggplot(data=mdf, aes(x=Year, y=value, group = Company, colour = Company)) +
geom_line() +
geom_point( size=4, shape=21, fill="white") +
facet_wrap( "Category" )
或者,您可以按相应变量对data.frame
进行子集化,并将各个图存储在列表中:
librayr("plyr")
ll <- dlply( mdf, "Category", function(x){
ggplot(data=x, aes(x=Year, y=value, group = Company, colour = Company)) +
geom_line() +
geom_point( size=4, shape=21, fill="white")
})
ll[["Category1"]]
答案 1 :(得分:0)
至少对于ggplot2,您需要使用 reshape2 包,以便将数据转换为稍微不同的格式。
让我们假设你有一个像这样的data.frame:
test <- structure(list(Company = structure(1:3, .Label = c("Company1",
"Company2", "Company3"), class = "factor"), X2011.1 = c(300L,
320L, 310L), X2013.1 = c(350L, 430L, 420L), X2011.2 = c(290,
305, 400), X2013.2 = c(300, 301, 305), X2011.3 = c(295, 300,
400), X2013.3 = c(290L, 400L, 410L)), .Names = c("Company", "X2011.1",
"X2013.1", "X2011.2", "X2013.2", "X2011.3", "X2013.3"), class = "data.frame", row.names = c(NA,
-3L))
暂时忽略丑陋,看起来像:
Company X2011.1 X2013.1 X2011.2 X2013.2 X2011.3 X2013.3
Company1 300 350 290 300 295 290
Company2 320 430 305 301 300 400
Company3 310 420 400 305 400 410
如果我们使用melt()
函数,我们可以看起来像这样:
melt(test) -> test.melt
test.melt
Using Company as id variables
Company variable value
1 Company1 X2011.1 300
2 Company2 X2011.1 320
3 Company3 X2011.1 310
4 Company1 X2013.1 350
5 Company2 X2013.1 430
6 Company3 X2013.1 420
7 Company1 X2011.2 290
8 Company2 X2011.2 305
然后使用公司或variable
作为ggplot2的分组因子。显然你会想要更明智地命名这些。 :)
e.g。你可以做到
ggplot(melt(test)) + geom_bar(aes(x = Company, y = value, fill = variable), stat = "identity", position = "dodge")
或其他什么。