web-dev-qa-db-ja.com

mutate_ifの正しい構文

NAmutate_ifを介して、dplyrの値をゼロに置き換えたいと思います。以下の構文:

set.seed(1)
mtcars[sample(1:dim(mtcars)[1], 5),
       sample(1:dim(mtcars)[2], 5)] <-  NA

require(dplyr)

mtcars %>% 
    mutate_if(is.na,0)

mtcars %>% 
    mutate_if(is.na, funs(. = 0))

エラーを返します:

vapply(tbl, p, logical(1), ...)のエラー:値は長さ1でなければなりませんが、FUN(X[[1]])結果は長さ32です

この操作の正しい構文は何ですか?

44
Konrad

このトリックを purrrチュートリアル から学び、dplyrでも機能します。この問題を解決するには2つの方法があります。
最初に、パイプの外部でカスタム関数を定義し、mutate_if()で使用します。

any_column_NA <- function(x){
    any(is.na(x))
}
replace_NA_0 <- function(x){
    if_else(is.na(x),0,x)
}
mtcars %>% mutate_if(any_column_NA,replace_NA_0)

次に、~.または.xの組み合わせを使用します(.x.に置き換えることができますが、他の文字や記号は使用できません)。

mtcars %>% mutate_if(~ any(is.na(.x)),~ if_else(is.na(.x),0,.x))
#This also works
mtcars %>% mutate_if(~ any(is.na(.)),~ if_else(is.na(.),0,.))

あなたの場合、mutate_all()を使用することもできます:

mtcars %>% mutate_all(~ if_else(is.na(.x),0,.x))

~を使用すると、匿名関数を定義できますが、.xまたは.は変数を表します。 mutate_if()の場合、.または.xは各列です。

33
Yifu Yan

mutate_ifの「if」は、行ではなくを選択することを意味します。たとえば、mutate_if(data, is.numeric, ...)は、データセット内のすべての数値列に対して変換を実行することを意味します。

数値列ですべてのNAをゼロに置き換える場合:

data %>% mutate_if(is.numeric, funs(ifelse(is.na(.), 0, .)))
43
Hong Ooi
mtcars %>% mutate_if(is.numeric, replace_na, 0)
11
Nettle

data.tablesetを使用できます

library(data.table)
setDT(mtcars)
for(j in seq_along(mtcars)){
  set(mtcars, i= which(is.na(mtcars[[j]])), j = j, value = 0)
 }
3
akrun

私はいつもdplyrのreplace_na関数に苦労しています

  replace(is.na(.),0)

これはあなたがやろうとしていることのために私のために働く。

0
Ashish Singhal