Разделить столбец, получить среднее значение для разделенных столбцов и обновить результат - PullRequest
0 голосов
/ 26 января 2019

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

Ниже приведен код, который я пробовал .. который не работает ..

test.val <- data.table(id = c(1, 2, 3), 
                       colA = c("100-150", "200", "300"), 
                       colB = c("15", "20-30", "10"))
test.A <- test.val[, lapply(.SD, function(x){strsplit(x, split = "-")}), .SDcols = c("colA", "colB")]
test.B[, lapply(.SD, mean), .SDcols = c("colA", "colB")]

В конце я хотел бы получить следующее:

   id colA colB
1:  1  125   15
2:  2  200   25
3:  3  300   10

Кто-нибудь, кто может мне помочь?Большое спасибо.

Ответы [ 2 ]

0 голосов
/ 26 января 2019

Другой вариант использования data.table

library(data.table)
cols <- c("colA", "colB")
for(j in cols) {
  tmp <- vapply(strsplit(test.val[[j]], "-"), 
                FUN = function(i) mean(as.numeric(i)), 
                FUN.VALUE = numeric(1))
  set(test.val, j = j, value = tmp)
}
test.val
#   id colA colB
#1:  1  125   15
#2:  2  200   25
#3:  3  300   10

Для заданного вектора

x <- c("100-150", "200", "300")

результат strsplit представляет собой список векторов символов

strsplit(x, "-")
#[[1]]
#[1] "100" "150"

#[[2]]
#[1] "200"

#[[3]]
#[1] "300"

Мы заключаем это в vapply и вычисляем среднее значение для каждого элемента после того, как мы преобразовали каждый вектор в числовое значение.

vapply(strsplit(x, "-"), function(x) mean(as.numeric(x)), numeric(1))
# [1] 125 200 300

Мы используем этот результат для замены каждого столбца, указанного в cols, используя data.table 's set функция.

0 голосов
/ 26 января 2019

Вот одна tidyverse возможность:

test.val %>%
 gather(var, val, -id) %>%
 separate(val, c("val1", "val2"), sep = "-", convert = TRUE) %>%
 mutate(res = rowMeans(.[, 3:4], na.rm = TRUE)) %>%
 select(-val1, -val2) %>%
 spread(var, res)

  id colA colB
1  1  125   15
2  2  200   25
3  3  300   10

На первом этапе выполняется преобразование данных из широкого в длинный формат. Затем он разделяет значения на два столбца. Наконец, он вычисляет среднее значение строки и преобразует данные обратно в исходный формат.

Учитывая, что у вас может быть более двух значений на столбец, который вы хотите разделить:

test.val %>%
 gather(var, val, -id) %>%
 mutate(val = strsplit(val, "-")) %>%
 unnest(val) %>%
 group_by(id, var) %>%
 mutate(res = mean(as.numeric(val))) %>%
 distinct(res) %>%
 spread(var, res)
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...