修改一行数据以获得漂亮的输出(摘要),重塑 - 将行拆分为新的多列

Modification of one row of data to get an nice looking output (summary), reshape - split rows to new multiple columns

我又需要你的帮助了。通常我知道如何解决我的问题,但在这种情况下我不知道。这是我的数据样本:

df <- t(data.frame(b = list(c('C:1874 N:3493','C:2642 A:7 M:1 N:2717','A:5298 N:69','C:5366 Y:1','A:5359 G:8'))))
row.names(df) <- 'x'
colnames(df) <- c('V1','V2','V3','V4','V5')
df

  V1              V2                      V3            V4           V5          
x "C:1874 N:3493" "C:2642 A:7 M:1 N:2717" "A:5298 N:69" "C:5366 Y:1" "A:5359 G:8"

我正在寻找像这样存储在 df 中的漂亮摘要 NA 可以用空格或零替换:

    V1    V2    V3    V4    V5
A   NA    7     5298  NA    5359
C   1874  2642  NA    5366  NA
N   3493  2717  69    NA    NA
M   NA    1     NA    NA    NA
Y   NA    NA    NA    1     NA
G   NA    NA    NA    NA    8

到目前为止,我知道如何轻松地将元素从一列拆分为新行:

library(tidyr)
separate_rows(as.data.frame(df), V1, sep = " ")

  V1     V2                    V3          V4         V5        
  <chr>  <chr>                 <chr>       <chr>      <chr>     
1 C:1874 C:2642 A:7 M:1 N:2717 A:5298 N:69 C:5366 Y:1 A:5359 G:8
2 N:3493 C:2642 A:7 M:1 N:2717 A:5298 N:69 C:5366 Y:1 A:5359 G:8

输出不是很好,因为所有剩余的列都填充了来自第一列的结果,但我想在 sapply() 中执行此操作并使用 cbind() 来获得一个数据框结果数据帧来自每个输入列。但不知道接下来会发生什么。如何将每个字母放在第一列并做出漂亮的总结。

提前致谢!

这就是你想要的:

library(tidyverse)

df %>% 
  t() %>% 
  as_tibble(rownames = "colname") %>% # two columns: 'colname' (V1...V5) and 'x' (values)
  separate_rows(x, sep = " ") %>% # spread 'x' over rows
  separate(x, c("rowname", "value"), sep = ":") %>% # separate letter and value into two columns 'rowname' and 'value' 
  pivot_wider(names_from = "colname", values_from = "value") %>% # pivot into the wide form you want
  arrange(rowname) # sort by rowname

这给出了

# A tibble: 6 x 6
  rowname V1    V2    V3    V4    V5   
  <chr>   <chr> <chr> <chr> <chr> <chr>
1 A       NA    7     5298  NA    5359 
2 C       1874  2642  NA    5366  NA   
3 G       NA    NA    NA    NA    8    
4 M       NA    1     NA    NA    NA   
5 N       3493  2717  69    NA    NA   
6 Y       NA    NA    NA    1     NA   

在基础 R 中你可以做到

FUN <- function(x) {
  s <- strsplit(x, split=":")
  d <- as.double(sapply(s, `[`, 2))
  setNames(as.data.frame(t(d)), lapply(s, `[`, 1))
}


l <- lapply(lapply(unlist(df), function(x) el(strsplit(x, " "))), FUN)
res <- as.data.frame(t(Reduce(function(...) merge(..., all=TRUE, sort=FALSE), l)))
res
#     V1   V2   V3   V4   V5
# A   NA    7 5298   NA 5359
# C 1874 2642   NA 5366   NA
# N 3493 2717   69   NA   NA
# M   NA    1   NA   NA   NA
# Y   NA   NA   NA    1   NA
# G   NA   NA   NA   NA    8