A plot histogram that visualizes each observation whose color is mapped to a second variable

I am looking for a way to show a histogram of values ​​( time2) with a bin width of 1, and the color of each observation ("count") will be mapped to the second variable ( diff).

enter image description here

df <- data.frame(person=seq(from=1, to=12, by=1),
                 time1=c(9, 9, 9, 8, 8, 8, 8, 7, 7, 6, 6, 5),
                 time2=c(9, 4, 3, 9, 6, 5, 4, 9, 3, 2, 1, 2))
df$diff <- df$time2-df$time1

, , : ggplot2. ? 12 , 1 2. 1 2. , , , 2,75, 1 2 2 6 . , , .

+4
3

geom_tile(). , - , dplyr/purr. x y.

df_plot = df %>%
  gather(time, value, time1:time2)

df_plot = df_plot %>%
  split(df_plot$time) %>%
  lapply(function(x) {x %>% group_by(value) %>% mutate(y=1:n())}) %>%
  bind_rows() %>%
  mutate(diff = factor(diff))

ggplot(df_plot) +
  geom_tile(aes(x = value, y = y, fill = diff)) +
  facet_wrap(~time) +
  theme_classic() + 
  scale_fill_brewer(type = "seq", palette = 3) +
  scale_x_continuous(breaks = 0:10) +
  xlab("") + ylab("")

. , .

enter image description here

+3
# load packages
library(ggplot2)

# calculate nth occurence of time 1 value 
new.df <- df %>% 
  group_by(time1) %>% 
  mutate(time1Index=1:n())

# plot time 1
p<- ggplot(new.df, aes(x = time1 , y=time1Index, fill = diff)) + geom_tile()
p + expand_limits(x = c(0, 10)) + xlab("") + ylab("")

# calculate nth occurence of time 2 value 
new.df2 <- df %>% 
  group_by(time2) %>% 
  mutate(time2Index=1:n())

# plot time 2
p2<- ggplot(new.df2, aes(x = time2 , y=time2Index, fill = diff)) + geom_tile()
p2 + expand_limits(x = c(0, 10)) +
  xlab("") + ylab("")
+1

, gridExtra, facet_wrap - Vlo geom_tile. df:

Libraries:

library(data.table)
library(reshape2)
library(ggplot2)
library(gridExtra)

Convert to data table, then add y values ​​for time1 and time2 with .Nand group for each

dt <- as.data.table(df)

dt[, y1  := 1:.N, by = time1][, y2 := 1:.N, by = time2]

Then create a separate ggplot object for each with specific scaling and color options:

p1 <- ggplot(dt) + 
  geom_tile(aes(x = time1, y = y1), fill = "white", col = "black") +
  coord_cartesian(xlim = c(0, 10), ylim = c(0.5, 4.5), expand = TRUE) +
  scale_x_continuous(breaks = 0:10)+
  theme_classic() +
  theme(axis.line.y = element_blank(),
        axis.ticks.y = element_blank(),
        axis.text.y = element_blank(),
        axis.title.y = element_blank(),
        plot.margin = unit(c(6,1,1,0.5), "cm")) 

p2 <- ggplot(dt) + 
  geom_tile(aes(x = time2, y = y2, fill = diff), col = "black") +
  scale_fill_gradientn(colours = c("#237018", "white", "red4"), values = c(0, 0.8, 1)) +
  coord_cartesian(xlim = c(0, 10), ylim = c(0.5, 4.5), expand = TRUE) +
  scale_x_continuous(breaks = 0:10) +
  theme_classic() + 
  theme(axis.line.y = element_blank(),
        axis.ticks.y = element_blank(),
        axis.text.y = element_blank(),
        axis.title.y = element_blank(),
        plot.margin = unit(c(6,1,1,0.5), "cm"),
        legend.position = c(0, 1.55),
        legend.direction = "horizontal")

Then use grid.arrangeto offset their adjacent objects:

grid.arrange(p1, p2, nrow = 1)

Conclusion:

enter image description here

Failed to get the right legend, maybe a little more work is needed.

+1
source

Source: https://habr.com/ru/post/1694150/


All Articles