Как выбрать данные из диапазона в пределах плотности в R - PullRequest
0 голосов
/ 18 сентября 2018

Не уверен, как справиться с этим - у меня есть распределение данных, где выбор данных на основе стандартного отклонения не включает все точки данных (данные более изменчивы на одном конце, чем на другом).Тем не менее, при построении графика плотности я вижу, что все данные вне 8-го синего кольца - это то, что я хочу выбрать.

Пример кода:

x <- sort(rnorm(1300, mean = 0, sd = 1))
y <- rnorm(1300, mean = 0, sd = 1)
x <- c(x, rnorm(300, mean = 4, sd = 2), rnorm(600, mean = -2, sd = 2))
y <- c(y, rnorm(300, mean = 3, sd = 4), rnorm(600, mean = -2, sd = 2))

mydata <- data.frame(x,y)

ggplot(data = mydata, aes(x = x, y = y)) +
  geom_point(cex = 0.5) +
  geom_density_2d()

1 Ответ

0 голосов
/ 18 сентября 2018

Я адаптировал это с http://slowkow.com/notes/ggplot2-color-by-density/. Под капотом geom_density_2d используется функция MASS::kde2d, поэтому мы также можем применить ее к базовым данным для подмножества по плотности.

set.seed(42)
x <- sort(rnorm(1300, mean = 0, sd = 1))
y <- rnorm(1300, mean = 0, sd = 1)
x <- c(x, rnorm(300, mean = 4, sd = 2), rnorm(600, mean = -2, sd = 2))
y <- c(y, rnorm(300, mean = 3, sd = 4), rnorm(600, mean = -2, sd = 2))

mydata <- data.frame(x,y) 

# Copied from http://slowkow.com/notes/ggplot2-color-by-density/
get_density <- function(x, y, n = 100) {
  dens <- MASS::kde2d(x = x, y = y, n = n)
  ix <- findInterval(x, dens$x)
  iy <- findInterval(y, dens$y)
  ii <- cbind(ix, iy)
  return(dens$z[ii])
}
mydata$density <- get_density(mydata$x, mydata$y)

Выбор точек на основе произвольного контура

РЕДАКТИРОВАТЬ: Изменено, чтобы разрешить выбор на основе уровней контура

# First create plot with geom_density
gg <- ggplot(data = mydata, aes(x = x, y = y)) +
  geom_point(cex = 0.5) +
  geom_density_2d(size = 1, n = 100)
gg

# Extract levels denoted by contours by going into the 
#   ggplot build object. I found these coordinates by 
#   examining the object in RStudio; Note, the coordinates 
#   would change if the layer order were altered.
gb <- ggplot_build(gg)
contour_levels <- unique(gb[["data"]][[2]][["level"]])
# contour_levels
# [1] 0.01 0.02 0.03 0.04 0.05 0.06 0.07 0.08

# Add layer that relies on given contour level
gg2 <- gg +
  geom_point(data = mydata %>% 
               filter(density <= contour_levels[1]), 
             color = "red", size = 0.5)
gg2

enter image description here

...