Вычислить rowMeans для диапазона столбца (номер переменной)
Я хочу вычислить rowMeans диапазона столбца, но не могу дать жестко запрограммированное значение для имен столбцов (например, c(C1,C3)) или диапазона (например, C1:C3), так как имена и диапазон являются переменными. Мой DF выглядит так:
> df
chr name age MGW.1 MGW.2 MGW.3 HEL.1 HEL.2 HEL.3
1 123 abc 12 10.00 19 18.00 12 13.00 -14
2 234 bvf 24 -13.29 13 -3.02 12 -0.12 24
3 376 bxc 17 -6.95 10 -18.00 15 4.00 -4
Это всего лишь пример, на самом деле у меня есть столбцы в MGW.1 ... MGW.196 и так далее. Здесь Вместо того, чтобы давать точные имена столбцов или точный диапазон, я хочу передать начальные значения имен столбцов и получить среднее значение для всех столбцов, имеющих эти инициалы. Что-то вроде: MGW=rowMeans(df[,MGW.*]), HEL=rowMeans(df[,HEL.*])
Итак, мой окончательный вывод должен выглядеть так:
> df
chr name age MGW Hel
1 123 abc 12 10.00 19
2 234 bvf 24 13.29 13
3 376 bxc 17 -6.95 10
Я знаю, что эти значения не верны, но это просто дать вам и идею. Во-вторых, я хочу удалить все эти строки из фрейма данных, который содержит NA во всей строке, кроме первых 3-х значений.
Вот dput для примера:
> dput(df)
structure(list(chr = c(123L, 234L, 376L), name = structure(1:3, .Label = c("abc",
"bvf", "bxc"), class = "factor"), age = c(12L, 24L, 17L), MGW.1 = c(10,
-13.29, -6.95), MGW.2 = c(19L, 13L, 10L), MGW.3 = c(18, -3.02,
-18), HEL.1 = c(12L, 12L, 15L), HEL.2 = c(13, -0.12, 4), HEL.3 = c(-14L,
24L, -4L)), .Names = c("chr", "name", "age", "MGW.1", "MGW.2",
"MGW.3", "HEL.1", "HEL.2", "HEL.3"), class = "data.frame", row.names = c(NA,
-3L))
2 ответа
Вот идея достижения желаемого результата без жесткого кодирования имен переменных:
library(dplyr)
library(tidyr)
df %>%
# remove rows where all values are NA except the first 3 columns
filter(rowSums(is.na(.[4:length(.)])) != length(.) - 3) %>%
# gather the data in a tidy format
gather(key, value, -(chr:age)) %>%
# separate the key column into label and num allowing
# to regroup by variables without hardcoding them
separate(key, into = c("label", "num")) %>%
group_by(chr, name, age, label) %>%
# calculate the mean
summarise(mean = mean(value, na.rm = TRUE)) %>%
spread(label, mean)
Я позволил себе изменить ваши исходные данные, чтобы показать, как логика будет соответствовать особым случаям. Например, здесь у нас есть строка (#4), где все значения, кроме первых 3 столбцов NA
s (в соответствии с вашими требованиями, этот ряд должен быть удален) и один, где есть сочетание NA
с и значения (#5). В этом случае я предположил, что мы хотели бы получить результат для MGW
так как есть значение в MGW.1
:
# chr name age MGW.1 MGW.2 MGW.3 HEL.1 HEL.2 HEL.3
#1 123 abc 12 10.00 19 18.00 12 13.00 -14
#2 234 bvf 24 -13.29 13 -3.02 12 -0.12 24
#3 376 bxc 17 -6.95 10 -18.00 15 4.00 -4
#4 999 zzz 21 NA NA NA NA NA NA
#5 888 aaa 12 10.00 NA NA NA NA NA
Который дает:
#Source: local data frame [4 x 5]
#Groups: chr, name, age [4]
#
# chr name age HEL MGW
#* <int> <fctr> <int> <dbl> <dbl>
#1 123 abc 12 3.666667 15.666667
#2 234 bvf 24 11.960000 -1.103333
#3 376 bxc 17 5.000000 -4.983333
#4 888 aaa 12 NaN 10.000000
Данные
df <- structure(list(chr = c(123L, 234L, 376L, 999L, 888L), name = structure(c(2L,
3L, 4L, 5L, 1L), .Label = c("aaa", "abc", "bvf", "bxc", "zzz"
), class = "factor"), age = c(12L, 24L, 17L, 21L, 12L), MGW.1 = c(10,
-13.29, -6.95, NA, 10), MGW.2 = c(19L, 13L, 10L, NA, NA), MGW.3 = c(18,
-3.02, -18, NA, NA), HEL.1 = c(12L, 12L, 15L, NA, NA), HEL.2 = c(13,
-0.12, 4, NA, NA), HEL.3 = c(-14L, 24L, -4L, NA, NA)), .Names = c("chr",
"name", "age", "MGW.1", "MGW.2", "MGW.3", "HEL.1", "HEL.2", "HEL.3"
), class = "data.frame", row.names = c("1", "2", "3", "4", "5"))
во-первых
Я думаю, что вы ищете это, чтобы получить среднее количество строк:
df$mean.Hel <- rowMeans(df[, grep("^HEL.", names(df))])
И чтобы впоследствии удалить столбцы:
df[, grep("^HEL.", names(df))] <- NULL
во-вторых
Удалить строки, которые имеют только NA
после первых трех элементов.
rows.delete <- which(rowSums(!is.na(df)[,4:ncol(df)]) == 0)
df <- df[!(1:nrow(df) %in% rows.delete),]