Как объединить таблицы частот с пропущенными значениями? - PullRequest
0 голосов
/ 07 ноября 2018

У меня есть следующий список таблиц:

    list(structure(c(`0` = 19L, `1` = 2L, `3` = 43L), .Dim = 3L, .Dimnames = structure(list(
    c("0", "1", "3")), .Names = ""), class = "table"), structure(c(`0` = 7L, 
`1` = 9L, `2` = 5L, `3` = 43L), .Dim = 4L, .Dimnames = structure(list(
    c("0", "1", "2", "3")), .Names = ""), class = "table"), structure(c(`0` = 14L, 
`1` = 2L, `2` = 4L, `3` = 44L), .Dim = 4L, .Dimnames = structure(list(
    c("0", "1", "2", "3")), .Names = ""), class = "table"), structure(c(`0` = 21L, 
`1` = 8L, `2` = 2L, `3` = 33L), .Dim = 4L, .Dimnames = structure(list(
    c("0", "1", "2", "3")), .Names = ""), class = "table"), structure(c(`0` = 23L, 
`1` = 3L, `2` = 1L, `3` = 37L), .Dim = 4L, .Dimnames = structure(list(
    c("0", "1", "2", "3")), .Names = ""), class = "table"), structure(c(`0` = 19L, 
`1` = 2L, `2` = 4L, `3` = 39L), .Dim = 4L, .Dimnames = structure(list(
    c("0", "1", "2", "3")), .Names = ""), class = "table"), structure(c(`0` = 22L, 
`1` = 1L, `2` = 4L, `3` = 37L), .Dim = 4L, .Dimnames = structure(list(
    c("0", "1", "2", "3")), .Names = ""), class = "table"))

Каждая таблица представляет собой список наблюдений значений 0, 1, 2 или 3. Однако не все значения представлены во всех таблицах, поэтому в некоторых таблицах отсутствуют столбцы. Я хотел бы, чтобы эти пропущенные значения были присвоены 0 в конечном выводе.

merge плохо работает со списками, а пометка rbind не работает, потому что не все таблицы имеют совпадающие столбцы.

Как я могу объединить эти таблицы в одну матрицу или data.frame с одним столбцом для каждого значения (0, 1, 2, 3) и одной строкой для каждого счетчика (7 в этом примере)?

Окончательный результат должен выглядеть следующим образом:

structure(list(`0` = c(19L, 7L, 14L, 21L, 23L, 19L, 22L), `1` = c(2L, 
9L, 2L, 8L, 3L, 2L, 1L), `2` = c(0L, 5L, 4L, 2L, 1L, 4L, 4L), 
    `3` = c(43L, 43L, 44L, 33L, 37L, 39L, 37L)), class = "data.frame", row.names = c(NA, 
-7L))

Ответы [ 2 ]

0 голосов
/ 07 ноября 2018

В базе R и при условии, что ваш список называется mylist, вы можете сделать что-то вроде следующего.

all_names <- sort(unique(unlist(lapply(mylist, names))))

res <- do.call("rbind", lapply(mylist, function(x) x[all_names]))
print(res)
#      0 1 <NA>  3
#[1,] 19 2   NA 43
#[2,]  7 9    5 43
#[3,] 14 2    4 44
#[4,] 21 8    2 33
#[5,] 23 3    1 37
#[6,] 19 2    4 39
#[7,] 22 1    4 37

Теперь вы можете либо принять это, либо сделать несколько правок, чтобы сделать его идеальным:

colnames(res) <- all_names  # Ensure correct colnames
res[is.na(res)] <- 0        # Overwrite NAs with 0
print(res)
#      0 1 2  3
#[1,] 19 2 0 43
#[2,]  7 9 5 43
#[3,] 14 2 4 44
#[4,] 21 8 2 33
#[5,] 23 3 1 37
#[6,] 19 2 4 39
#[7,] 22 1 4 37
0 голосов
/ 07 ноября 2018

Мы конвертируем отдельные наборы данных в data.frame с помощью map и используем bind_rows, чтобы связать наборы данных в один набор данных

library(tidyverse)
map(lst, as.data.frame.list, check.names = FALSE) %>% 
          bind_rows
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...