Andre Elrico
Andre Elrico

Reputation: 11480

Set values NA from first occurence of Pattern to end

Is there a faster/ shorter way to set values after and including match to NA ?

vec <- 1:10;vec[c(3,5,7)]<-c(NA,NaN,"remove")
#"1"      "2"      NA       "4"      "NaN"    "6"      "remove" "8"      "9"      "10"    

Desired Outcome:

#"1"      "2"      NA       "4"      "NaN"    "6"      NA       NA       NA       NA

My code:

vec[{grep("^remove$",vec)[1]}:length(vec)]<-NA

Please note:

In that case, we assume there will be a "remove" element prominent. So the solution does not have to take care of the case that there isn't any.

Upvotes: 2

Views: 61

Answers (4)

Ronak Shah
Ronak Shah

Reputation: 389047

Not sure if this is shorter or faster but here is one alternative :

vec[which.max(vec == "remove"):length(vec)] <- NA
vec
#[1] "1"   "2"   NA    "4"   "NaN" "6"   NA    NA    NA    NA   

Here , we find the first occurrence of "remove" using which.max and then add NA's till the end of the vector.


OP has mentioned that there is a "remove" element always present so we need not take care of other case however, in case we still want to keep a check we can add an additional condition.

inds <- vec == "remove"
if (any(inds)) {
  vec[which.max(inds) : length(vec)] <- NA
}

Upvotes: 3

Onyambu
Onyambu

Reputation: 79238

We can also just extend the vec to the desired length:

`length<-`(vec[1:(which(vec=="remove")-1)],length(vec))
 [1] "1"   "2"   NA    "4"   "NaN" "6"   NA    NA    NA    NA   

Upvotes: 0

Frank
Frank

Reputation: 66819

You can use match to stop searching after the first match is found:

m = match("remove", vec) - 1L
if (is.na(m)){
  vec 
} else {
  c(head(vec, m), rep(vec[NA_integer_], length(vec)-m))
}

You'd have to have a pretty large vector to notice a speed difference, though, I guess. Alternately, this might prove faster:

m = match("remove", vec)
if (!is.na(m)){
  vec[m:length(vec)] <- NA 
}

Upvotes: 3

akrun
akrun

Reputation: 887213

We can use cumsum on a logical vector

vec[cumsum(vec %in% "remove") > 0] <- NA

Upvotes: 2

Related Questions