Ваша цель - хорошая идея для целей сравнения!
Однако, похоже, что функция violoplot()
не реализует эту опцию - на своей странице документации. Таким образом, ваш подход должен быть способом go, учитывая, что для каждой группы набор записей, удовлетворяющих условию дополнения (т. Е. Все, кроме записей в группе), отличается . Это означает, что вам нужен один другой объект (по одному на группу) для хранения этой информации, и это именно то, что вы делаете.
Тем не менее, ниже приведен фрагмент кода, который вносит следующие улучшения в ваш код:
- он уменьшает память (поскольку он создает данные для каждой группы дополнений и добавляет блок-график к графику Righttaway - без сохранения его во фрейме данных, содержащем записи для всех групп дополнения)
- it сокращает время выполнения (поскольку он вычисляет уникальные
BBB
значения только один раз - до for
l oop с использованием table()
) - это более читабельно :)
(обратите внимание, что я не использую функцию violoplot()
, потому что я У меня не установлен пакет vioplot
, я просто использую функцию boxplot()
, но вы сможете расширить ее до своих скриптов)
Тестовые данные для построения
I изменил пример данных, чтобы сделать сюжет, который лучше передает то, что мы Затем, следующим образом:
- Я сократил количество групп (значения
BBB
) только до первых 3 букв - Для каждой группы я создаю нормальное распределение среднее значение которого равно порядковому значению буквы (т. е. 1, 2 или 3) (это позволяет различать распределение цифры c переменная
AAA
в каждой группе)
-
# The data to plot
set.seed(117)
groups = LETTERS[1:3]
df = data.frame(BBB=sample(groups,1000,replace=TRUE))
df_sp = split(df, df$BBB)
df_sp = lapply(df_sp, transform, AAA = rnorm(length(BBB), mean=as.numeric(BBB), sd=0.2))
df = unsplit(df_sp, df$BBB)
head(df)
BBB AAA
1 C 2.7884212
2 A 0.7924213
3 B 2.0032205
4 B 2.2402493
5 C 3.0513685
6 A 1.2553530
Пример графика
Сначала мы генерируем блокпосты по группам (ваш «правый» план скрипки), а затем добавляем блокпосты дополнения каждой группы (ваш «левый» план скрипки) ).
# Groups to plot
groups = names(table(df$BBB))
# Reduce margins to make plot bigger
op = par(mar=c(5.1,4.1,0.1,0.1))
# Generate the boxplots by group (this would be your "right" violin plots)
boxplot(AAA ~ BBB, data=df, at=(1:length(groups)), boxwex=0.2)
# Add the distribution of the complement (this would be your "left" violin plots)
grp_idx = 0 # This variable is used to define the X location to add the boxplot to.
# You would also need it in the violoplot() function for the 'at=' parameter
for (grp in groups) {
grp_idx = grp_idx + 1
# Complement data to plot for the group
df_complement = df[ df$BBB!=grp, ]
df_complement$BBB = grp
# The 'at' parameter indicates the correct X location to add the boxplot to
# which is shifted a little bit (by +0.2) to avoid overlap with the boxplot of the group
boxplot(AAA ~ BBB, data=df_complement, col="red", add=TRUE, at=grp_idx+0.2, boxwex=0.2)
}
# Restore margins
par(op)
Обратите внимание, что нам , а не нужно предварительно рассчитать диапазон оси Y, чтобы каждый add
ed бокс-график вписывался в базовые блок-графики по графу группы, потому что этот оригинальный блок-график уже покрывает ВСЕ диапазон оси Y, присутствующий в данных, - поскольку он отображает ВСЕ данные.
Приведенный выше код выдает:
Таким образом, ваша задача - адаптировать приведенный выше код для использования функции violoplot()
.