0

我正在寻找用颜色表示来自单独数据列的值的堆叠条形图,并仅使用 R 中的基本图形添加准确的颜色条。还有一篇关于这个的帖子,但它非常混乱,最后并不能帮助我回答我的问题。

# create reproducible data
d <- read.csv(text='Day,Location,Length,Amount
            1,4,3,1.1
            1,3,1,.32
            1,2,3,2.3
            1,1,3,1.1
            2,0,0,0
            3,3,3,1.8
            3,2,1,3.54
            3,1,3,1.1',header=T)

# colors will be based on values in the Amount column
v1 <- d$Amount
# make some colors based on Amount - normalized
z <- v1/max(v1)*1000
colrs <- colorRampPalette(c('lightblue','blue','black'))(1000)[z]

# create a 2d table of the data needed for plotting
tab <- xtabs(Length ~ Location + Day, d)
# create a stacked bar plot
barplot(tab,col=colrs,space=0)

# create a color bar
plotr::color.bar

这肯定会产生一个颜色编码的堆叠条形图,但颜色并不能准确地代表数据。

对于第 1 天,位置 4 和 1 的颜色应相同。另一个例子,金额列中的第一个和最后一个条目相同,但左列顶部的颜色与右列底部不匹配。

另外,我发现了如何在不同的帖子上制作彩条,它使用plotr::color.bar代码,但plotr显然不是一个包,我不知道如何继续。

如何使颜色与适当的部分相匹配并添加准确的颜色条?

4

3 回答 3

1

我希望“相当杂乱无章”的帖子不是我对如何在 r 中以水平堆积条形图的风格创建时间序列图的答案!很好,没有冒犯。

该解决方案可以适应您的数据,如下所示:

## store data
df <- read.csv(text='Day,Location,Length,Amount\n1,4,3,1.1\n1,3,1,.32\n1,2,3,2.3\n1,1,3,1.1\n2,0,0,0\n3,3,3,1.8\n3,2,1,3.54\n3,1,3,1.1',header=T);

## extract bar segment lengths from Length and bar segment colors from a function of Amount, both stored in a logical matrix form
lengths <- xtabs(Length~Location+Day,df);
amounts <- xtabs(Amount~Location+Day,df);
colors <- matrix(colorRampPalette(c('lightblue','blue','black'))(1001)[amounts/max(amounts)*1000+1],nrow(amounts));

## transform lengths into an offset matrix to appease design limitation of barplot(). Note that colors will be flattened perfectly to accord with this offset matrix
lengthsOffset <- as.matrix(setNames(reshape(cbind(id=1:length(lengths),stack(as.data.frame(unclass(lengths)))),dir='w',timevar='ind')[-1],colnames(lengths)));
lengthsOffset[is.na(lengthsOffset)] <- 0;

## draw plot
barplot(lengthsOffset,col=colors,space=0,xlab='Day',ylab='Length');

偏移堆积条形图


笔记

  • colrs <- colorRampPalette(c('lightblue','blue','black'))(1000)[z]在您的问题中,您尝试使用z将 8 个原始Amount值转换为“每千”形式来构建颜色矢量。这有一个小缺陷,因为其中一个z元素为零,这不是有效的索引值。这就是为什么你有 7 种颜色,而应该是 8 种颜色。我在代码中修复了这个问题,将每千分之一的值加 1 并生成 1001 种颜色。
  • 还与生成颜色有关,而不是只生成 8 种颜色(即每个原始Amount值一种),我生成了一个完整的颜色矩阵来平行lengths矩阵(您tab在代码中调用了该矩阵)。这个颜色矩阵实际上可以直接用作传递给barplot()'col参数的颜色向量,因为在内部它被展平为一个向量(至少在概念上)并且将对应于我们将传递给参数的偏移条段barplot()长度height(见下注)。
  • 正如我在上述帖子中更详细描述的那样,该解决方案的关键是创建一个条形段长度的“偏移矩阵”,相邻列中的值为零,以便可以为每个段分配不同的颜色。我lengthsOffsetlengths矩阵创建它。
  • 请注意,可能有点违反直觉,height参数中较低的索引值被绘制barplot()为较低的段,反之亦然,这意味着当您在终端中打印该数据时的文本显示与它在条形图中的显示方式垂直反转. 如果你想要相反的顺序,你可以垂直反转lengthsOffset矩阵和colors向量,但我没有在我的代码中这样做。

作为参考,这里是所有的数据结构:

df;
##   Day Location Length Amount
## 1   1        4      3   1.10
## 2   1        3      1   0.32
## 3   1        2      3   2.30
## 4   1        1      3   1.10
## 5   2        0      0   0.00
## 6   3        3      3   1.80
## 7   3        2      1   3.54
## 8   3        1      3   1.10
lengths;
##         Day
## Location 1 2 3
##        0 0 0 0
##        1 3 0 3
##        2 3 0 1
##        3 1 0 3
##        4 3 0 0
amounts;
##         Day
## Location    1    2    3
##        0 0.00 0.00 0.00
##        1 1.10 0.00 1.10
##        2 2.30 0.00 3.54
##        3 0.32 0.00 1.80
##        4 1.10 0.00 0.00
colors;
##      [,1]      [,2]      [,3]
## [1,] "#ADD8E6" "#ADD8E6" "#ADD8E6"
## [2,] "#4152F5" "#ADD8E6" "#4152F5"
## [3,] "#0000B3" "#ADD8E6" "#000000"
## [4,] "#8DB1EA" "#ADD8E6" "#0000FA"
## [5,] "#4152F5" "#ADD8E6" "#ADD8E6"
lengthsOffset;
##    1 2 3
## 1  0 0 0
## 2  3 0 0
## 3  3 0 0
## 4  1 0 0
## 5  3 0 0
## 6  0 0 0
## 7  0 0 0
## 8  0 0 0
## 9  0 0 0
## 10 0 0 0
## 11 0 0 0
## 12 0 0 3
## 13 0 0 1
## 14 0 0 3
## 15 0 0 0
于 2015-05-27T17:04:23.127 回答
0

根据以下评论:

library(ggplot2)
ggplot(d, aes(x = Day, y = Length)) + geom_bar(aes(fill = Amount, order = Location), stat = "identity") 
于 2015-05-27T15:29:19.810 回答
0

我认为这是定义颜色的错误,条形图只需要 5 种颜色,因为有 5 个位置,并且其中一种颜色不会被使用,因为位置 1 每天都有零元素。

使固定:

colrs <- colorRampPalette(c('yellow', 'lightblue','blue','black', 'lightblue'))(5)

修复 colrs 矢量后的输出

请注意,没有绘制“黄色”,因为它的组中有 0 个观察值(在来自 OP 的样本数据中)

于 2015-05-27T15:45:30.313 回答