#r #ggplot2
#r #ggplot2
Вопрос:
Вопрос
Я хотел бы использовать ggplot geom_boxplot
и использовать свои собственные столбцы данных для сегментов квантилей вместо тех, которые возвращаются stat_boxplot
.
Данные после выполнения некоторых преобразований выглядят следующим образом:
> allquartile
T method s.0% s.25% s.50% s.75% s.100%
1 2 LDA -196.76273 -190.38842 -184.01411 -177.63979 -171.26548
2 3 LDA -171.53987 -166.16923 -160.79859 -115.28652 -69.77446
3 4 LDA -161.17590 -157.61372 -149.71026 -124.68926 -69.77446
4 5 LDA -194.10553 -179.83165 -175.14337 -168.46104 -159.07206
После долгих поисков и поисков я понял, что моя команда построения графика должна выглядеть следующим образом:
p <- ggplot(allquartile,aes(x=T, ymin=`s.0%`, lower=`s.25%`,
middle=`s.50%`, upper=`s.75%`,
ymax=`s.100%`, color=method))
geom_boxplot(stat="identity")
Это должно использовать 0% в качестве минимального, 25% в качестве нижнего и т. Д. И т. Д. Но когда я пытаюсь отобразить p
, я получаю следующую ошибку:
Error in eval(expr, envir, enclos) : object 's.0%' not found
Calls: print ... lapply -> is.vector -> lapply -> FUN -> eval -> eval
Я также пытался использовать aes_string
вместо aes
, и вместо этого я получаю эту ошибку:
Error in aes_string(x = T, ymin = `s.0%`, lower = `s.25%`, middle = `s.50%`, :
object 's.0%' not found
Я довольно новичок как в R, так и в ggplot2, поэтому я не совсем уверен, как это интерпретировать, но я предполагаю, что это из-за .
in s.0%
.
Я был бы очень признателен за любые предложения о том, как обойти это.
Редактировать: я покопался больше, и я думаю, что это связано с моим непониманием метода квантилей. Я создал allquartile
с помощью этой команды:
allquartile <-aggregate(list(s=topicquality$score), list(T=topicquality$T,method=topicquality$method),FUN=quantile,probs=seq(0, 1, .25))
И я понимаю, что нет столбцов с именами score.0%
, score.25%
, и т.д. Есть только score
столбец с 5 значениями. Итак, это сводится к следующему: как мне получить доступ к этим 5 значениям внутри score
?
РЕШЕНИЕ
Я обнаружил проблему с моим набором данных. Как я упоминал в своем редактировании, столбцы score.0%
, score.25%
, и т.д. не существовали в зависимости от того, как я сформировал фрейм данных. Например, выполнение colnames(allquartile)
вернуло:
[1] "T" "method" "score"
Получается, что score
столбец представляет собой вектор значений. Запуск allquartile$score
дает мне:
0% 25% 50% 75% 100%
[1,] -196.7627 -190.3884 -184.0141 -177.6398 -171.26548
[2,] -171.5399 -166.1692 -160.7986 -115.2865 -69.77446
[3,] -161.1759 -157.6137 -149.7103 -124.6893 -69.77446
[4,] -194.1055 -179.8316 -175.1434 -168.4610 -159.07206
[5,] -200.1544 -174.2835 -167.7209 -145.3432 -129.54586
Затем я могу получить доступ к значениям каждого отдельного квантиля, выполнив
> allquartile$score[,1]
[1] -196.7627 -171.5399 -161.1759 -194.1055 -200.1544
Я недостаточно знаком с R, чтобы знать, что это за структура данных, но я бы назвал это матрицей. Так что, как и любой хороший матричный объект, m[,column]
возвращает значения столбца, а m[row,]
возвращает значения строки и m[row, column]
получает значение ячейки.
Имея это в виду, я понял, что команда propper для построения графика должна быть
p <- ggplot(allquartile,
aes(x=T,
ymin=score[,1],
lower=score[,2],
middle=score[,3],
upper=score[,4],
ymax=score[,5],
color=method))
geom_boxplot(stat="identity")
И это отображает все идеально.
Спасибо всем за хорошие предложения, хотя они и не устранили проблему, они очень помогли разобраться.
Комментарии:
1.
.
Вероятно, это не проблема, но я бы поспорил%
, что это так. Попробуйте прочитать?make.names
.2. Я думал, что это хорошо, но я нашел пример, в котором
p <- ggplot(data,aes(x=.id, ymin=`5%`, lower=`25%`, middle=`50%`, upper=`75%`, ymax=`95%`)) geom_boxplot(stat="identity")
правильно отображались чужие данные.3. Ну, я просто пытался подтолкнуть вас к тому, чтобы попробовать простой первый проход при отладке: установите имена столбцов на
allquartile
что-то абсолютно безопасное (без символов).4.
ymax='s.1000%'
может быть лишнее0
, и у вас, похоже, есть множество «и`5. @Henry: Упс, это наверняка опечатка, но проблема все еще сохраняется. кроме того, все, что связано с именами s.x%, является обратным
Ответ №1:
На самом деле, основываясь на ваших правках, я думаю, что ваша настоящая проблема заключается в том, что вы не должны были использовать aggregate
. Если применяемая вами функция возвращает несколько значений (например quantile
), aggregate
по умолчанию возвращает результаты в несколько неудобном формате, который вы наблюдали.
Происходит вот что. Фрейм данных, что несколько сбивает с толку, на самом деле является списком, причем каждый столбец является элементом списка. Единственным требованием является то, что каждый «столбец» имеет одинаковое количество строк. Итак, вы получаете фрейм данных обратно с тремя «столбцами»: третий столбец — это просто матрица!
Это aggregate
возможно с помощью, но есть более удобные инструменты. (Например, вы могли бы вызвать cbind(allquartile[,1:2],allquartile[,3])
, чтобы создать фрейм данных «правильных» размеров.)
Например, очень популярный ddply
из plyr
пакета. Вот пример, в котором используются некоторые составленные данные, но соблюдается общая структура ваших данных:
topicquality <- data.frame(score = runif(20),
T = rep(letters[1:2],each = 10),
method = rep(letters[3:4],length.out = 20))
ddply(topicquality,.(T,method),FUN = function(x,...){quantile(x$score,...)},probs = seq(0,1,0.25))
Вы заметите, что это вернет фрейм данных ожидаемых размеров, но вам все равно придется иметь дело с неудобными именами столбцов. Это лучше всего решать в функции, которую вы применяете к каждой части:
myQuantile <- function(x,...){
tmp <- quantile(x,...)
names(tmp) <- NULL #Or something else convenient
tmp
}
ddply(topicquality,.(T,method),FUN = myQuantile,probs = seq(0,1,0.25))
Комментарии:
1. Это имеет большой смысл. Я просто использую aggregate, поскольку это то, что уже было написано кем-то другим, для построения более простых вещей, таких как среднее, медианное и максимальное. Мне удалось заставить все работать, как указано выше, с помощью агрегатных и матричных операций, но я попробую сделать это. Я действительно нахожу довольно странным, что мой третий «столбец» является матрицей.
Ответ №2:
Вот как это решить. Проблема в именах ваших столбцов. Если вы введете names(allquartile)
, вы заметите, что ваши имена столбцов и т.д. s.0.
s.25.
Я бы рекомендовал избегать всех знаков препинания в именах столбцов, за исключением _
или .
.
require(stringr)
names(allquartile) = str_replace_all(names(allquartile), "\.", '')
p <- ggplot(allquartile2, aes_string(x = "T", ymin = "s0", lower = "s25",
middle = "s50", upper = "s75", ymax = "s100", color = "method"))
geom_boxplot(stat = "identity")