29

My data called "dat":

A   B   C
NA  2   NA
1   2   3
1   NA  3
1   2   3

I want to be all rows to be removed if it has an NA in column B:

A   B   C
NA  2   NA
1   2   3
1   2   3

na.omit(dat) removes all rows with an NA not just the ones where the NA is in column B.

Also I'd like to know how to this for NA value in two columns.

I appreciate all advice!

ah bon
  • 9,293
  • 12
  • 65
  • 148
user9259005
  • 465
  • 1
  • 4
  • 12
  • 4
    Try with `is.na` i.e. `dat[!is.na(dat$B),]` or `subset(dat, !is.na(B))` or `library(dplyr);dat %>% filter(!is.na(B))` or `data.table` `setDT(dat)[!is.na(B)]` – akrun Feb 07 '18 at 08:14

4 Answers4

58

The easiest solution is to use is.na():

df[!is.na(df$B), ]

which gives you:

   A B  C
1 NA 2 NA
2  1 2  3
4  1 2  3
clemens
  • 6,653
  • 2
  • 19
  • 31
  • Why do you need the comma "," after "(df$B)" ? – Emil Krabbe Mar 11 '21 at 13:45
  • 6
    when you subset a data.frame with square brackets, the element before the comma applies to rows, the element after the comma to columns. if you don't use the comma, R will assume you are selecting columns. – clemens Mar 11 '21 at 15:46
  • 1
    This answer provides a big speed improvement over the tidyverse option! Average speed of 200us (base) vs 1400ms (tidyverse) – JJ Fantini Aug 31 '22 at 16:34
25

there is an elegant solution if you use the tidyverse!

it contains the library tidyr that provides the method drop_na which is very intuitive to read.

So you just do:

library(tidyverse)

dat %>% drop_na("B")

OR

dat %>% drop_na(B)

if B is a column name

Jake
  • 683
  • 6
  • 5
Agile Bean
  • 6,437
  • 1
  • 45
  • 53
  • I'd add that this answer is useful if passing strings to functions which are intended to be used as column names. – Bradford Aug 04 '22 at 16:43
6

try this:

df<-data.frame(A=c(NA,1,1,1),B=c(2,2,NA,2),C=c(NA,3,3,3))
df<-df[-which(is.na(df$B)),]
df
   A B  C
1 NA 2 NA
2  1 2  3
4  1 2  3
jyjek
  • 2,627
  • 11
  • 23
-1

This should work

dat <- dat[dat['B'].notnull()]  
ah bon
  • 9,293
  • 12
  • 65
  • 148