按行绑定具有不同列名称的数据框

时间:2020-10-16 11:00:34

标签: r dataframe dplyr

我将此Excel工作表作为数据框列表导入。我想将列表合并到一个数据框中。 --max-old-space-size=30000使我可以轻松地将数据帧加在一起,但是问题是我有一个变量/列,每个数据帧中都有不同的名称。 bind_rows()默认情况下将创建两个单独的列,其中其他数据帧中的数据为空值。如何加入这些专栏?

示例代码:

bind_row()

理想的结果:

# Sample dataframes
df1 <- tibble(A = c(1,2,3),
              B = c("X","Y","Z"),
              C = c(T,F,F)
                  )
df2 <- tibble(A = c(3,4,5),
              B = c("U","V","W"),
              D = c(T,T,F)
)

# List of dataframes
my_ls <- list(df1, df2)
my_ls
[[1]]
# A tibble: 3 x 3
      A B     C    
  <dbl> <chr> <lgl>
1     1 X     TRUE 
2     2 Y     FALSE
3     3 Z     FALSE

[[2]]
# A tibble: 3 x 3
      A B     D    
  <dbl> <chr> <lgl>
1     3 U     TRUE 
2     4 V     TRUE 
3     5 W     FALSE

# Creating joined dataframe:
my_df <- bind_rows(my_ls)
my_df
# Current outcome: A tibble: 6 x 4
      A B     C     D    
  <dbl> <chr> <lgl> <lgl>
1     1 X     TRUE  NA   
2     2 Y     FALSE NA   
3     3 Z     FALSE NA   
4     3 U     NA    TRUE 
5     4 V     NA    TRUE 
6     5 W     NA    FALSE

当前,我一直在将# Desired outcome: A tibble: 6 x 3 A B C <dbl> <chr> <lgl> 1 1 X TRUE 2 2 Y FALSE 3 3 Z FALSE 4 3 U TRUE 5 4 V TRUE 6 5 W FALSE mutate()一起使用,在其中检查哪一列不为空(case_when())。这行得通,但我忍不住想必须有一个更简单的方法。

!is.na()

3 个答案:

答案 0 :(得分:2)

您可以bind_rows,然后使用coalesce选择非NA值:

library(dplyr)

bind_rows(my_ls) %>% mutate(C = coalesce(C, D)) %>% select(A:C)

#      A  B     C    
#  <dbl> <chr> <lgl>
#1     1 X     TRUE 
#2     2 Y     FALSE
#3     3 Z     FALSE
#4     3 U     TRUE 
#5     4 V     TRUE 
#6     5 W     FALSE

答案 1 :(得分:1)

为打破tidyverse表示歉意,以便快速回答

expl <- read.table(text= " A B     C     D    
1     1 X     TRUE  NA   
2     2 Y     FALSE NA   
3     3 Z     FALSE NA   
4     3 U     NA    TRUE 
5     4 V     NA    TRUE 
6     5 W     NA    FALSE")

expl$E <- ifelse(is.na(expl$C), expl$D, expl$C)

print(expl)

或者也许

expl[,c("C", "D")] %>% rowMeans(na.rm = TRUE) %>% as.logical()

编辑:将后者翻译为整洁的

expl %>% select("C", "D") %>% rowMeans(na.rm = TRUE) %>% as.logical()

在第一个评论后进行编辑:

如果您想获得更多控制权,则可能应该在类似于以下示例的函数中编写每种情况下想要做的事情:

library(magrittr)

expl <- read.table(text= " A B     C     D    
1     1 X     TRUE  NA   
2     2 Y     FALSE NA   
3     3 Z     FALSE NA   
4     3 U     NA    TRUE 
5     4 V     NA    TRUE 
6     5 W     NA    FALSE
7     7 I     NA    NA
8     9 J     TRUE  TRUE")

myfun <- function(a, b){
  if(is.na(a) & is.na(b)) 
     return(NA)
  if(!is.na(a) & !is.na(b)) {
    warning("too much information, a and b set!")
    return(NaN)
  }
  return(max(a, b, na.rm=TRUE))
}

myfun = Vectorize(myfun)

myfun(expl$C, expl$D) %>% as.logical()

答案 2 :(得分:1)

在@KarthikS之后,您可以在绑定之前重命名列。我使用rename_with的方法不需要将列按特定顺序排列。为了说明这一点,我使用了一些不同的示例数据帧:

library(purrr)
library(dplyr)

d1 <- data.frame(A = 1, B = 2, C = 3)
d2 <- data.frame(A = 4, B = 5, D = 6)
d3 <- data.frame(D = 7, A = 8, B = 9)

d <- list(d1, d2, d3)

map(d, ~ rename_with(.x, ~ "C", matches("^D$"))) %>% 
  bind_rows()
#>   A B C
#> 1 1 2 3
#> 2 4 5 6
#> 3 8 9 7

现在有四个数据集:

d <- list(df1, df2)
map(d, ~ rename_with(.x, ~ "C", matches("^D$"))) %>% 
  bind_rows()
#> # A tibble: 6 x 3
#>       A B     C    
#>   <dbl> <chr> <lgl>
#> 1     1 X     TRUE 
#> 2     2 Y     FALSE
#> 3     3 Z     FALSE
#> 4     3 U     TRUE 
#> 5     4 V     TRUE 
#> 6     5 W     FALSE

如果我们添加一个具有不同顺序的附加数字:

df3 <- tibble(D = c(T,T,F),
              A = c(7,8,9),
              B = c("A","B","C"))

d <- list(df1, df2, df3)
map(d, ~ rename_with(.x, ~ "C", matches("^D$"))) %>% 
  bind_rows()
#> # A tibble: 9 x 3
#>       A B     C    
#>   <dbl> <chr> <lgl>
#> 1     1 X     TRUE 
#> 2     2 Y     FALSE
#> 3     3 Z     FALSE
#> 4     3 U     TRUE 
#> 5     4 V     TRUE 
#> 6     5 W     FALSE
#> 7     7 A     TRUE 
#> 8     8 B     TRUE 
#> 9     9 C     FALSE

reprex package(v0.3.0)于2020-10-16创建

相关问题