Многократное применение AVE для средств вычислительной группы в кадре данных

Следующий код отдельно создает групповые средства x а также y в соответствии с group, Предположим, что у меня есть ряд переменных, для которых повторяется одна и та же операция.

Как бы вы предложили действовать, чтобы получить тот же результат с помощью одной команды? (Я полагаю, необходимо принять tapply, но я не совсем уверен в этом..).

x=seq(1,11,by=2); y=seq(2,12,by=2); group=rep(1:2, each=3)
dat <- data.frame(cbind(group, x, y))

dat$m_x <- ave(dat$x, dat$group)
dat$m_y <- ave(dat$y, dat$group)
dat

Большое спасибо.

3 ответа

Решение

Альтернативные решения с использованием data.table а также plyr пакеты:

1) Использование data.table

require(data.table)
dt <- data.table(dat, key="group")
# Following @Matthew's comment, edited:
dt[, `:=`(m_x = mean(x), m_y = mean(y)), by=group]

Выход:

   group  x  y m_x m_y
1:     1  1  2   3   4
2:     1  3  4   3   4
3:     1  5  6   3   4
4:     2  7  8   9  10
5:     2  9 10   9  10
6:     2 11 12   9  10

2) используя plyr и преобразовать:

require(plyr)
ddply(dat, .(group), transform, m_x=mean(x), m_y=mean(y))

выход:

  group  x  y m_x m_y
1     1  1  2   3   4
2     1  3  4   3   4
3     1  5  6   3   4
4     2  7  8   9  10
5     2  9 10   9  10
6     2 11 12   9  10

3) используя plyr и numcolwise (обратите внимание на уменьшенный вывод):

ddply(dat, .(group), numcolwise(mean))

Выход:

  group x  y
1     1 3  4
2     2 9 10

Предполагая, что у вас есть более двух столбцов, вы хотели бы использовать apply применять ave к каждому столбцу в матрице.

x=seq(1,11,by=2); y=seq(2,12,by=2); group=rep(1:2, each=3)
dat <- cbind(x, y)

ave.dat <- apply(dat, 2, function(column) ave(column, group))
#       x  y
# [1,]  1  2
# [2,]  3  4
# [3,]  5  6
# [4,]  7  8
# [5,]  9 10
# [6,] 11 12

Вы также можете использовать aggregate():

dat2 <- data.frame(dat, aggregate(dat[,-1], by=list(dat$group), mean)[group, -1])
dat2
    group  x  y x.1 y.1
1       1  1  2   3   4
1.1     1  3  4   3   4
1.2     1  5  6   3   4
2       2  7  8   9  10
2.1     2  9 10   9  10
2.2     2 11 12   9  10
row.names(dat2) <- rownames(dat)
colnames(dat2) <- gsub("(.)\\.1", "m_\\1", colnames(dat2))
dat2
  group  x  y m_x m_y
1     1  1  2   3   4
2     1  3  4   3   4
3     1  5  6   3   4
4     2  7  8   9  10
5     2  9 10   9  10
6     2 11 12   9  10    

Если имена переменных больше чем один символ, вам нужно изменить вызов gsub().

Другие вопросы по тегам