如何在ggplot中绘制表格对象

时间:2018-12-24 17:51:17

标签: r ggplot2 visualization

代码:

library(plyr)
library(datasets)
data("iris")

iris$Sepal.Length

size <- c()
for (s in iris$Sepal.Length){
  if (s < 5.8){
    size <- c(size, "SMALL")
  } else if(s >= 5.8){
    size <- c(size, "LARGE")
  }
}
iris$Size <- size
plot(table(iris$Species, iris$Size))

情节:

image1


我想知道如何在ggplot中绘制这种东西。

我有这个(取决于先前的代码):

ggplot(as.data.frame(table(iris$Species, iris$Size)), 
       aes(x=Var1, y=Freq, fill=Var2)) +
  geom_bar(stat="identity", position="fill") + 
  theme_fivethirtyeight() + 
  theme(axis.text.x = element_text(size=15),
        text = element_text(size=15)) +
  scale_x_discrete(labels=c("S1", "S2", "S3")) + 
  labs(y = "Percentage") + 
  labs(x = "") + 
  theme(axis.title = element_text()) + 
  ggtitle("Something about iris stuff") + 
  scale_fill_discrete(name = "Size")

image1

传达相似的信息,但是不一样。

所以-如何在ggplot中像plot(table(a, b))一样制作表格。我不希望它在样式上完全相同(或者我只是使用base),但是我更喜欢在表中显示比例的方式,而不是我在gg中使用的条形

此处能够传递表格对象的功能非常有用,因为我正在for循环内生成具有基数的图

编辑-在循环内绘制的代码

我将在此帖子完成后对其进行编辑,以使其更整洁,我不想 删除人们当前正在参考的内容

以下是通过绘制表格对象在循环内绘制的一些代码。我不是 确定我将如何在ggplot中进行此操作。

rm(list=ls())

library(plyr)
library(datasets)
data("iris")
set.seed(1234)

iris$Sep.Size <- c("SMALL", "LARGE")[(iris$Sepal.Length >= 5.8) + 1]
# create an additional categorical variable, purely for the sake of plotting it
iris$Data.2 <- cut(
  rnorm(150, 10, 2), 
  c(-Inf, 8, 10, 11, Inf),
  labels = c('a', 'b', 'c', 'd'),
  include.lowest = TRUE)


iris.2 <- data.frame(data = iris$Data.2, sepsize = iris$Sep.Size, species = iris$Species)

# plotting tables using a loop - one of them will be nonsense, but the others are usable. 
for ( i in 1:dim(iris.2)[2]){
  t = table(iris.2$species, iris.2[,i])
  plot(t)
}

作为结果,创建了3个图

2 个答案:

答案 0 :(得分:2)

以下内容并非您所要的,但它以某种自然的方式解决了您的问题。

它使用包dplyr将数据集通过管道传输到as.data.frame。并转到ggplot

library(ggplot2)
library(dplyr)
library(datasets)

data("iris")

size <- c("SMALL", "LARGE")[(iris$Sepal.Length >= 5.8) + 1L]
tbl <- table(iris[5:6])

tbl %>%
  as.data.frame() %>%
  ggplot(aes(Species, Freq, fill = Size)) + 
  geom_bar(stat="identity", position="fill")

缺点是,您必须加载一个额外的程序包。

对于新向量size,可以使用

创建

findInterval

Size_Values <- c("SMALL", "LARGE")
i <- findInterval(iris$Sepal.Length, c(0, 5.8, Inf))
size2 <- Size_Values[i]

identical(size, size2)
#[1] TRUE

cut

在这种情况下,输出是"factor"类的对象。

size3 <- cut(iris$Sepal.Length, c(0, 5.8, Inf), labels = Size_Values,
    include.lowest = TRUE, right = FALSE)

identical(size, as.character(size3))
#[1] TRUE

编辑。

为了使用新数据解决问题中的更改,以下代码在同一图形窗口中绘制了两个表。在问题中以可重复的方式创建数据集iris.2,在调用内置PRNG函数之一之前设置伪RNG种子。

# plotting tables using a loop
# the columns to plot are determined by 
# these 2 instructions
ref <- "species"
others <- names(iris.2)[names(iris.2) != ref]

old_par <- par(mfrow = c(1, 2))
for(i in others){
  tbl <- table(iris.2[[ref]], iris.2[[i]])
  plot(tbl)
}
par(old_par)

答案 1 :(得分:2)

也许使用ggmosaic包?

library(ggplot2)
library(ggmosaic)
library(datasets)

size <- c("SMALL", "LARGE")[(iris$Sepal.Length >= 5.8) + 1L]

ggplot(data = iris) +
  geom_mosaic(aes(x = product(Size, Species), fill = Size), na.rm = TRUE)

然后您可以根据需要设置图表的格式。

编辑:

要解决请求的循环(基于原始问题中创建的iris.2数据框,并使用上述Rui Barradas的代码),可以使用:

ref <- "species"
others <- names(iris.2)[names(iris.2) != ref]

for (i in others){
  tmp <- iris.2[, c(ref, i)]
  p <- ggplot(data = tmp) + 
         geom_mosaic(aes(x = product(species, !!ensym(i)), fill = !!ensym(i)), na.rm = TRUE)
  print(p)  
}

这将为针对ggplot的每个变量创建一个不同的镶嵌species。当然,您可以在循环内相应地设置图表的格式,甚至可以将每个图保存在列表中,然后根据需要将它们绘制在同一页面上。