Al unir data.frames a lo largo de una clave, y una clave tiene un valor faltante (NA), mi intuición fue que las filas con una clave NA no deberían coincidir en el segundo data.frame. Para mi sorpresa, si hay NA en ambos data.frames, dplyr los empareja como si fueran valores.

Esto es aún más confuso porque se discutió extensamente sobre los problemas en el repositorio dplyr ver aquí y parece estar resuelto! Si es así, no veo cómo esta es la solución correcta; o tal vez me falta algo

Estoy usando dplyr 0.7.4


t1 <- data.frame(a = as.character(c("1", "2", NA, NA, "4", "2")), b = c(1, 2, 3, 3, 4, 5), stringsAsFactors = FALSE)
t2 <- data.frame(a = as.character(c("1", "2", NA)), c = c("b", "n", "i"), stringsAsFactors = FALSE)
library(dplyr)
t1
#>      a b
#> 1    1 1
#> 2    2 2
#> 3 <NA> 3
#> 4 <NA> 3
#> 5    4 4
#> 6    2 5
t2
#>      a c
#> 1    1 b
#> 2    2 n
#> 3 <NA> i
left_join(t1, t2, by = "a")
#>      a b    c
#> 1    1 1    b
#> 2    2 2    n
#> 3 <NA> 3    i
#> 4 <NA> 3    i
#> 5    4 4 <NA>
#> 6    2 5    n

Cuando, de hecho, hubiera esperado lo siguiente:

#>      a b    c
#> 1    1 1    b
#> 2    2 2    n
#> 3 <NA> 3 <NA>
#> 4 <NA> 3 <NA>
#> 5    4 4 <NA>
#> 6    2 5    n
8
AndrewMacDonald 21 feb. 2018 a las 14:51

2 respuestas

La mejor respuesta

La solución es usar el argumento na_matches = "never". Esto fue señalado por Dani Rabaiotti y Hadley Wickham en Twitter.

Este argumento está documentado en el método left_join para la clase tbl_df: ?left_join.tbl_df

4
AndrewMacDonald 21 feb. 2018 a las 12:44

Este comportamiento es el mismo que merge (aunque con algunos reordenamientos).

merge(t1,t2,all.x=T)
     a b    c
1    1 1    b
2    2 2    n
3    2 5    n
4    4 4 <NA>
5 <NA> 3    i
6 <NA> 3    i

Puede obtener el resultado esperado configurando incomparables=NA:

merge(t1,t2,all.x=T,incomparables=NA)
     a b    c
1    1 1    b
2    2 2    n
3    2 5    n
4    4 4 <NA>
5 <NA> 3 <NA>
6 <NA> 3 <NA>

En dplyr esta opción no parece estar documentada, pero mirando dplyr:::left_join.tbl_df puedes ver que na_matches parece prometedor. Algunos juegos revelan que debes darle el valor "never".

left_join(t1,t2,by="a",na_matches="never")
     a b    c
1    1 1    b
2    2 2    n
3 <NA> 3 <NA>
4 <NA> 3 <NA>
5    4 4 <NA>
6    2 5    n
0
James 21 feb. 2018 a las 12:44